def test_is_loaded(self): """Check load status of a channel. """ data = np.random.rand(3, 3) self.chan = Channel(name="newchan") self.assert_(not self.chan.is_loaded()) self.chan = Channel(name="newchan", data=data) self.assert_(self.chan.is_loaded())
def test_as_image(self): """Check the geo_image version of the channel. """ data = np.random.rand(3, 3) self.chan = Channel(name="newchan", data=data) img = self.chan.as_image(False) self.assert_(np.allclose(img.channels[0], data)) self.assertEqual(img.mode, "L") img = self.chan.as_image(True) self.assertEqual(img.channels[0].max(), 1) self.assertEqual(img.channels[0].min(), 0)
def test_check_range(self): """Check the range of a channel. """ self.chan = Channel(name="newchan") self.assertRaises(ValueError, self.chan.check_range) numb = np.random.uniform(10) self.assertRaises(ValueError, self.chan.check_range, numb) # ndarray data = np.random.rand(3, 3) self.chan = Channel(name="newchan", data=data) min_range = (data.max() - data.min()) / 2 self.assert_(np.all(data == self.chan.check_range(min_range))) zeros = np.zeros_like(data) min_range = (data.max() - data.min()) + E self.assert_(np.all(zeros == self.chan.check_range(min_range))) # masked array mask = np.array(np.random.rand(3, 3) * 2, dtype=int) mask[1, 1] = False data = np.ma.array(data, mask=mask) self.chan = Channel(name="newchan", data=data) min_range = (data.max() - data.min()) / 2 self.assert_(np.all(data == self.chan.check_range(min_range))) self.assertEquals(data.count(), self.chan.check_range(min_range).count()) zeros = np.zeros_like(data) min_range = (data.max() - data.min()) + E self.assert_(np.all(zeros == self.chan.check_range(min_range))) data = np.ma.array(data, mask=True) self.chan = Channel(name="newchan", data=data) self.assertEquals(0, self.chan.check_range(min_range).count()) self.assertEquals(data.count(), self.chan.check_range(min_range).count()) # Wrong type arguments self.assertRaises(TypeError, self.chan.check_range, random_string(4)) self.assertRaises(TypeError, self.chan.check_range, [np.random.uniform()])
def test_str(self): """String output for a channel. """ self.chan = Channel(name="newchan", wavelength_range=(1., 2., 3.), resolution=1000) self.assertEqual( str(self.chan), "'newchan: (1.000,2.000,3.000)μm, resolution 1000m," " not loaded'") self.chan.data = np.random.rand(3, 3) self.assertEqual( str(self.chan), "'newchan: (1.000,2.000,3.000)μm, " "shape (3, 3), " "resolution 1000m'")
def test_str(self): """String output for a channel. """ self.chan = Channel(name="newchan", wavelength_range=(1.0, 2.0, 3.0), resolution=1000) self.assertEqual(str(self.chan), "'newchan: (1.000,2.000,3.000)μm, resolution 1000m," " not loaded'") self.chan.data = np.random.rand(3, 3) self.assertEqual(str(self.chan), "'newchan: (1.000,2.000,3.000)μm, " "shape (3, 3), " "resolution 1000m'")
def test_cmp(self): """Comparison of channels. """ self.chan = Channel(name="newchan") self.chan2 = Channel(name="mychan") self.assertTrue(self.chan > self.chan2) self.chan = Channel(name="newchan") self.chan2 = "mychan" self.assertTrue(self.chan > self.chan2) self.chan = Channel(name="newchan") self.chan2 = Channel(name="newchan") self.assert_(self.chan == self.chan2) self.chan = Channel(wavelength_range=(1.0, 2.0, 3.0)) self.chan2 = Channel(name="newchan") self.assert_(self.chan < self.chan2) self.chan = Channel(name="newchan") self.chan2 = Channel(name="_mychan") self.assert_(self.chan < self.chan2) self.chan = Channel(name="_newchan") self.chan2 = Channel(name="mychan") self.assert_(self.chan > self.chan2) self.chan = Channel(name=random_string(4), wavelength_range=(1.0, 2.0, 3.0)) self.chan2 = Channel(name=random_string(4), wavelength_range=(4.0, 5.0, 6.0)) self.assert_(self.chan < self.chan2) self.chan = Channel(name="_" + random_string(4), wavelength_range=(1.0, 2.0, 3.0)) self.chan2 = Channel(name=random_string(4), wavelength_range=(4.0, 5.0, 6.0)) self.assert_(self.chan > self.chan2)
def test_init(self): """Creation of a channel. """ self.assertRaises(ValueError, Channel) # Name self.chan = Channel(name="newchan") self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, 0) self.assert_(self.chan.data is None) numb = int(np.random.uniform(100000)) self.assertRaises(TypeError, Channel, name=numb) numb = np.random.uniform() * 100000 self.assertRaises(TypeError, Channel, name=numb) # Resolution numb = int(np.random.uniform(100000)) self.assertRaises(ValueError, Channel, resolution=numb) numb = int(np.random.uniform(100000)) self.chan = Channel(name="newchan", resolution=numb) self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, numb) self.assert_(self.chan.data is None) self.assertRaises(TypeError, Channel, name="newchan", resolution="a") # Wavelength numbs = [np.random.uniform(100), np.random.uniform(100), np.random.uniform(100)] numbs.sort() self.chan = Channel(wavelength_range=numbs) self.assertEqual(self.chan.name, None) self.assertEqual(self.chan.wavelength_range, numbs) self.assertEqual(self.chan.resolution, 0) self.assert_(self.chan.data is None) self.assertRaises(TypeError, Channel, wavelength_range=numbs[0:1]) numbs.sort(reverse=True) self.assertRaises(ValueError, Channel, wavelength_range=numbs) numbs = [int(np.random.uniform(100)), int(np.random.uniform(100)), int(np.random.uniform(100))] numbs.sort() self.assertRaises(TypeError, Channel, wavelength_range=numbs) self.assertRaises(TypeError, Channel, wavelength_range=random_string(4)) numb = np.random.uniform(100000) self.assertRaises(TypeError, Channel, wavelength_range=numb) numb = int(np.random.uniform(100000)) self.assertRaises(TypeError, Channel, wavelength_range=numb) # Data data = np.random.rand(3, 3) self.assertRaises(ValueError, Channel, data=data) self.chan = Channel(name="newchan", data=data) self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, 0) self.assert_(np.all(self.chan.data == data)) mask = np.array(np.random.rand(3, 3) * 2, dtype=int) data = np.ma.array(data, mask=mask) self.chan = Channel(name="newchan", data=data) self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, 0) self.assert_(np.all(self.chan.data == data)) self.assertRaises(TypeError, Channel, name="newchan", data=random_string(4)) numb = np.random.uniform(100000) self.assertRaises(TypeError, Channel, name="newchan", data=numb) numb = int(np.random.uniform(100000)) self.assertRaises(TypeError, Channel, name="newchan", data=numb) numbs = [np.random.uniform(100), np.random.uniform(100), np.random.uniform(100)] self.assertRaises(TypeError, Channel, name="newchan", data=numbs)
def _load02(filename): """Load data from a netcdf4 file, cf-satellite v0.2 (2012-02-03). """ rootgrp = Dataset(filename, 'r') # processed variables processed = set() # Currently satpy does not like unicode (so much). satellite_name, satellite_number = [str(i) for i in rootgrp.platform.rsplit("-", 1)] time_slot = rootgrp.variables["time"].getValue()[0] time_slot = num2date(time_slot, TIME_UNITS) processed |= set(["time"]) try: service = str(rootgrp.service) except AttributeError: service = "" instrument_name = str(rootgrp.instrument) try: orbit = str(rootgrp.orbit) except AttributeError: orbit = None try: scene = GenericFactory.create_scene(satellite_name, satellite_number, instrument_name, time_slot, orbit, None, service) except NoSectionError: scene = VisirCompositer(time_slot=time_slot) scene.satname = satellite_name scene.number = satellite_number scene.service = service dim_chart = {} for var_name, var in rootgrp.variables.items(): varname = None try: varname = var.standard_name except AttributeError: try: varname = var.long_name except AttributeError: pass if varname in ["band_data", "Band data"]: LOG.debug("Found some data: " + var_name) dims = var.dimensions for dim in dims: dim_chart[dim] = var_name for cnt, dim in enumerate(dims): if dim.startswith("band"): break data = var data.set_auto_maskandscale(False) area = None try: area_var_name = getattr(var,"grid_mapping") area_var = rootgrp.variables[area_var_name] proj4_dict = {} for attr, projattr in MAPPING_ATTRIBUTES.items(): try: the_attr = getattr(area_var, attr) if projattr == "proj": proj4_dict[projattr] = PROJNAME[the_attr] elif(isinstance(projattr, (list, tuple))): try: for i, subattr in enumerate(the_attr): proj4_dict[projattr[i]] = subattr except TypeError: proj4_dict[projattr[0]] = the_attr else: proj4_dict[projattr] = the_attr except AttributeError: pass y_name, x_name = dims[:cnt] + dims[cnt + 1:] x__ = rootgrp.variables[x_name][:] y__ = rootgrp.variables[y_name][:] if proj4_dict["proj"] == "geos": x__ *= proj4_dict["h"] y__ *= proj4_dict["h"] x_pixel_size = abs((np.diff(x__)).mean()) y_pixel_size = abs((np.diff(y__)).mean()) llx = x__[0] - x_pixel_size / 2.0 lly = y__[-1] - y_pixel_size / 2.0 urx = x__[-1] + x_pixel_size / 2.0 ury = y__[0] + y_pixel_size / 2.0 area_extent = (llx, lly, urx, ury) try: # create the pyresample areadef from pyresample.geometry import AreaDefinition area = AreaDefinition("myareaid", "myareaname", "myprojid", proj4_dict, len(x__), len(y__), area_extent) except ImportError: LOG.warning("Pyresample not found, " "cannot load area descrition") processed |= set([area_var_name, x_name, y_name]) LOG.debug("Grid mapping found and used.") except AttributeError: LOG.debug("No grid mapping found.") try: area_var = getattr(var,"coordinates") coordinates_vars = area_var.split(" ") lons = None lats = None for coord_var_name in coordinates_vars: coord_var = rootgrp.variables[coord_var_name] units = getattr(coord_var, "units") if(coord_var_name.lower().startswith("lon") or units.lower().endswith("east") or units.lower().endswith("west")): lons = coord_var[:] elif(coord_var_name.lower().startswith("lat") or units.lower().endswith("north") or units.lower().endswith("south")): lats = coord_var[:] if lons.any() and lats.any(): try: from pyresample.geometry import SwathDefinition area = SwathDefinition(lons=lons, lats=lats) except ImportError: LOG.warning("Pyresample not found, " "cannot load area descrition") processed |= set(coordinates_vars) LOG.debug("Lon/lat found and used.") except AttributeError: LOG.debug("No lon/lat found.") names = rootgrp.variables[dim][:] scales = data.scale_factor offsets = data.add_offset if len(names) == 1: scales = np.array([scales]) offsets = np.array([offsets]) LOG.info("Scales and offsets: %s %s %s" % (str(names), str(scales), str(offsets))) for nbr, name in enumerate(names): name = str(name) try: if cnt == 0: chn_data = data[nbr, :, :].squeeze() if cnt == 1: chn_data = data[:, nbr, :].squeeze() if cnt == 2: chn_data = data[:, :, nbr].squeeze() scene[name] = (np.ma.masked_equal(chn_data, data._FillValue) * scales[nbr] + offsets[nbr]) scene[name].info["units"] = var.units except KeyError: from satpy.channel import Channel scene.channels.append(Channel(name)) if area is not None: scene[name].area = area processed |= set([var_name, dim]) non_processed = set(rootgrp.variables.keys()) - processed for var_name in non_processed: var = rootgrp.variables[var_name] if not (hasattr(var, "standard_name") or hasattr(var, "long_name")): LOG.info("Delayed processing of " + var_name) continue dims = var.dimensions if len(dims) != 1: LOG.info("Don't know what to do with " + var_name) continue dim = dims[0] if var.standard_name == "radiation_wavelength": names = rootgrp.variables[dim][:] for nbr, name in enumerate(names): name = str(name) scene[name].wavelength_range[1] = var[nbr] try: bnds = rootgrp.variables[var.bounds][:] for nbr, name in enumerate(names): name = str(name) scene[name].wavelength_range[0] = bnds[nbr, 0] scene[name].wavelength_range[2] = bnds[nbr, 1] processed |= set([var.bounds]) except AttributeError: pass processed |= set([var_name]) non_processed = set(rootgrp.variables.keys()) - processed if len(non_processed) > 0: LOG.warning("Remaining non-processed variables: " + str(non_processed)) return scene
def test_sunzen_corr(self): '''Test Sun zenith angle correction. ''' import datetime as dt chan = Channel(name='test') original_value = 10. chan.data = original_value * np.ones((2, 11)) lats = np.zeros((2, 11)) # equator lons = np.array([np.linspace(-90, 90, 11), np.linspace(-90, 90, 11)]) # Equinox, so the Sun is at the equator time_slot = dt.datetime(2014, 3, 20, 16, 57) new_ch = chan.sunzen_corr(time_slot, lonlats=(lons, lats), limit=80.) # Test minimum after correction, accuracy of three decimals is enough #self.assertTrue(np.abs(10.000 - np.min(new_ch.data)) < 10**-3) self.assertAlmostEqual(10.000, np.min(new_ch.data), places=3) # Test maximum after correction self.assertAlmostEqual(57.588, np.max(new_ch.data), places=3) # There should be ten values at zenith angle >= 80 deg, and # these are all equal self.assertTrue(np.where(new_ch.data == \ np.max(new_ch.data))[0].shape[0] == 10) # All values should be larger than the starting values self.assertTrue(np.all(new_ch.data > original_value)) # Channel name self.assertEqual(new_ch.name, chan.name + '_SZC') # Test channel name in the info dict self.assertEqual(new_ch.name, chan.info['sun_zen_corrected']) # Test with several locations and arbitrary data chan = Channel(name='test2') chan.data = np.array( [[0., 67.31614275, 49.96271995, 99.41046645, 29.08660989], [87.61007584, 79.6683524, 53.20397351, 29.88260374, 62.33623915], [60.49283004, 54.04267222, 32.72365906, 91.44995651, 32.27232955], [63.71580638, 69.57673795, 7.63064373, 32.15683105, 9.05786335], [65.61434337, 33.2317155, 18.77672384, 30.13527574, 23.22572904]]) lons = np.array([[ 116.28695847, 164.1125604, 40.77223701, -113.54699788, 133.15558442 ], [-17.18990601, 75.17472034, 12.81618371, -40.75524952, 40.70898002], [ 42.74662341, 164.05671859, -166.58469404, -58.16684483, -144.97963063 ], [ 46.26303645, -167.48682034, 170.28131412, -17.80502488, -63.9031154 ], [ -107.14829679, -147.66665952, -0.75970554, 77.701768, -130.48677807 ]]) lats = np.array([ [-51.53681682, -83.21762788, 5.91008672, 22.51730385, 66.83356427], [82.78543163, 23.1529456, -7.16337152, -68.23118425, 28.72194953], [31.03440852, 70.55322517, -83.61780288, 29.88413938, 25.7214828], [-19.02517922, -19.20958728, -14.7825735, 22.66967876, 67.6089238], [45.12202477, 61.79674149, 58.71037615, -62.04350423, 13.06405864] ]) time_slot = dt.datetime(1998, 8, 1, 10, 0) # These are the expected results results = np.array([[ 0., 387.65821593, 51.74080022, 572.48205988, 138.96586013 ], [ 227.24857818, 105.53045776, 62.24134162, 172.0870564, 64.12902666 ], [ 63.08646652, 311.21934562, 188.44804188, 526.63931022, 185.84893885 ], [82.86856236, 400.6764648, 43.9431259, 46.58056343, 36.04457644], [ 377.85794388, 191.3738223, 27.55002934, 173.54213642, 133.75164285 ]]) new_ch = chan.sunzen_corr(time_slot, lonlats=(lons, lats), limit=80.) self.assertAlmostEqual(np.max(results - new_ch.data), 0.000, places=3)
def test_cmp(self): """Comparison of channels. """ self.chan = Channel(name="newchan") self.chan2 = Channel(name="mychan") self.assertTrue(self.chan > self.chan2) self.chan = Channel(name="newchan") self.chan2 = "mychan" self.assertTrue(self.chan > self.chan2) self.chan = Channel(name="newchan") self.chan2 = Channel(name="newchan") self.assert_(self.chan == self.chan2) self.chan = Channel(wavelength_range=(1., 2., 3.)) self.chan2 = Channel(name="newchan") self.assert_(self.chan < self.chan2) self.chan = Channel(name="newchan") self.chan2 = Channel(name="_mychan") self.assert_(self.chan < self.chan2) self.chan = Channel(name="_newchan") self.chan2 = Channel(name="mychan") self.assert_(self.chan > self.chan2) self.chan = Channel(name=random_string(4), wavelength_range=(1., 2., 3.)) self.chan2 = Channel(name=random_string(4), wavelength_range=(4., 5., 6.)) self.assert_(self.chan < self.chan2) self.chan = Channel(name="_" + random_string(4), wavelength_range=(1., 2., 3.)) self.chan2 = Channel(name=random_string(4), wavelength_range=(4., 5., 6.)) self.assert_(self.chan > self.chan2)
def test_init(self): """Creation of a channel. """ self.assertRaises(ValueError, Channel) # Name self.chan = Channel(name="newchan") self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, 0) self.assert_(self.chan.data is None) numb = int(np.random.uniform(100000)) self.assertRaises(TypeError, Channel, name=numb) numb = np.random.uniform() * 100000 self.assertRaises(TypeError, Channel, name=numb) # Resolution numb = int(np.random.uniform(100000)) self.assertRaises(ValueError, Channel, resolution=numb) numb = int(np.random.uniform(100000)) self.chan = Channel(name="newchan", resolution=numb) self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, numb) self.assert_(self.chan.data is None) self.assertRaises(TypeError, Channel, name="newchan", resolution="a") # Wavelength numbs = [ np.random.uniform(100), np.random.uniform(100), np.random.uniform(100) ] numbs.sort() self.chan = Channel(wavelength_range=numbs) self.assertEqual(self.chan.name, None) self.assertEqual(self.chan.wavelength_range, numbs) self.assertEqual(self.chan.resolution, 0) self.assert_(self.chan.data is None) self.assertRaises(TypeError, Channel, wavelength_range=numbs[0:1]) numbs.sort(reverse=True) self.assertRaises(ValueError, Channel, wavelength_range=numbs) numbs = [ int(np.random.uniform(100)), int(np.random.uniform(100)), int(np.random.uniform(100)) ] numbs.sort() self.assertRaises(TypeError, Channel, wavelength_range=numbs) self.assertRaises(TypeError, Channel, wavelength_range=random_string(4)) numb = np.random.uniform(100000) self.assertRaises(TypeError, Channel, wavelength_range=numb) numb = int(np.random.uniform(100000)) self.assertRaises(TypeError, Channel, wavelength_range=numb) # Data data = np.random.rand(3, 3) self.assertRaises(ValueError, Channel, data=data) self.chan = Channel(name="newchan", data=data) self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, 0) self.assert_(np.all(self.chan.data == data)) mask = np.array(np.random.rand(3, 3) * 2, dtype=int) data = np.ma.array(data, mask=mask) self.chan = Channel(name="newchan", data=data) self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, 0) self.assert_(np.all(self.chan.data == data)) self.assertRaises(TypeError, Channel, name="newchan", data=random_string(4)) numb = np.random.uniform(100000) self.assertRaises(TypeError, Channel, name="newchan", data=numb) numb = int(np.random.uniform(100000)) self.assertRaises(TypeError, Channel, name="newchan", data=numb) numbs = [ np.random.uniform(100), np.random.uniform(100), np.random.uniform(100) ] self.assertRaises(TypeError, Channel, name="newchan", data=numbs)
def test_sunzen_corr(self): """Test Sun zenith angle correction. """ import datetime as dt chan = Channel(name="test") original_value = 10.0 chan.data = original_value * np.ones((2, 11)) lats = np.zeros((2, 11)) # equator lons = np.array([np.linspace(-90, 90, 11), np.linspace(-90, 90, 11)]) # Equinox, so the Sun is at the equator time_slot = dt.datetime(2014, 3, 20, 16, 57) new_ch = chan.sunzen_corr(time_slot, lonlats=(lons, lats), limit=80.0) # Test minimum after correction, accuracy of three decimals is enough # self.assertTrue(np.abs(10.000 - np.min(new_ch.data)) < 10**-3) self.assertAlmostEqual(10.000, np.min(new_ch.data), places=3) # Test maximum after correction self.assertAlmostEqual(57.588, np.max(new_ch.data), places=3) # There should be ten values at zenith angle >= 80 deg, and # these are all equal self.assertTrue(np.where(new_ch.data == np.max(new_ch.data))[0].shape[0] == 10) # All values should be larger than the starting values self.assertTrue(np.all(new_ch.data > original_value)) # Channel name self.assertEqual(new_ch.name, chan.name + "_SZC") # Test channel name in the info dict self.assertEqual(new_ch.name, chan.info["sun_zen_corrected"]) # Test with several locations and arbitrary data chan = Channel(name="test2") chan.data = np.array( [ [0.0, 67.31614275, 49.96271995, 99.41046645, 29.08660989], [87.61007584, 79.6683524, 53.20397351, 29.88260374, 62.33623915], [60.49283004, 54.04267222, 32.72365906, 91.44995651, 32.27232955], [63.71580638, 69.57673795, 7.63064373, 32.15683105, 9.05786335], [65.61434337, 33.2317155, 18.77672384, 30.13527574, 23.22572904], ] ) lons = np.array( [ [116.28695847, 164.1125604, 40.77223701, -113.54699788, 133.15558442], [-17.18990601, 75.17472034, 12.81618371, -40.75524952, 40.70898002], [42.74662341, 164.05671859, -166.58469404, -58.16684483, -144.97963063], [46.26303645, -167.48682034, 170.28131412, -17.80502488, -63.9031154], [-107.14829679, -147.66665952, -0.75970554, 77.701768, -130.48677807], ] ) lats = np.array( [ [-51.53681682, -83.21762788, 5.91008672, 22.51730385, 66.83356427], [82.78543163, 23.1529456, -7.16337152, -68.23118425, 28.72194953], [31.03440852, 70.55322517, -83.61780288, 29.88413938, 25.7214828], [-19.02517922, -19.20958728, -14.7825735, 22.66967876, 67.6089238], [45.12202477, 61.79674149, 58.71037615, -62.04350423, 13.06405864], ] ) time_slot = dt.datetime(1998, 8, 1, 10, 0) # These are the expected results results = np.array( [ [0.0, 387.65821593, 51.74080022, 572.48205988, 138.96586013], [227.24857818, 105.53045776, 62.24134162, 172.0870564, 64.12902666], [63.08646652, 311.21934562, 188.44804188, 526.63931022, 185.84893885], [82.86856236, 400.6764648, 43.9431259, 46.58056343, 36.04457644], [377.85794388, 191.3738223, 27.55002934, 173.54213642, 133.75164285], ] ) new_ch = chan.sunzen_corr(time_slot, lonlats=(lons, lats), limit=80.0) self.assertAlmostEqual(np.max(results - new_ch.data), 0.000, places=3)
class TestChannel(unittest.TestCase): """Class for testing the Channel class. """ chan = None chan2 = None def test_init(self): """Creation of a channel. """ self.assertRaises(ValueError, Channel) # Name self.chan = Channel(name="newchan") self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, 0) self.assert_(self.chan.data is None) numb = int(np.random.uniform(100000)) self.assertRaises(TypeError, Channel, name=numb) numb = np.random.uniform() * 100000 self.assertRaises(TypeError, Channel, name=numb) # Resolution numb = int(np.random.uniform(100000)) self.assertRaises(ValueError, Channel, resolution=numb) numb = int(np.random.uniform(100000)) self.chan = Channel(name="newchan", resolution=numb) self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, numb) self.assert_(self.chan.data is None) self.assertRaises(TypeError, Channel, name="newchan", resolution="a") # Wavelength numbs = [ np.random.uniform(100), np.random.uniform(100), np.random.uniform(100) ] numbs.sort() self.chan = Channel(wavelength_range=numbs) self.assertEqual(self.chan.name, None) self.assertEqual(self.chan.wavelength_range, numbs) self.assertEqual(self.chan.resolution, 0) self.assert_(self.chan.data is None) self.assertRaises(TypeError, Channel, wavelength_range=numbs[0:1]) numbs.sort(reverse=True) self.assertRaises(ValueError, Channel, wavelength_range=numbs) numbs = [ int(np.random.uniform(100)), int(np.random.uniform(100)), int(np.random.uniform(100)) ] numbs.sort() self.assertRaises(TypeError, Channel, wavelength_range=numbs) self.assertRaises(TypeError, Channel, wavelength_range=random_string(4)) numb = np.random.uniform(100000) self.assertRaises(TypeError, Channel, wavelength_range=numb) numb = int(np.random.uniform(100000)) self.assertRaises(TypeError, Channel, wavelength_range=numb) # Data data = np.random.rand(3, 3) self.assertRaises(ValueError, Channel, data=data) self.chan = Channel(name="newchan", data=data) self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, 0) self.assert_(np.all(self.chan.data == data)) mask = np.array(np.random.rand(3, 3) * 2, dtype=int) data = np.ma.array(data, mask=mask) self.chan = Channel(name="newchan", data=data) self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, 0) self.assert_(np.all(self.chan.data == data)) self.assertRaises(TypeError, Channel, name="newchan", data=random_string(4)) numb = np.random.uniform(100000) self.assertRaises(TypeError, Channel, name="newchan", data=numb) numb = int(np.random.uniform(100000)) self.assertRaises(TypeError, Channel, name="newchan", data=numb) numbs = [ np.random.uniform(100), np.random.uniform(100), np.random.uniform(100) ] self.assertRaises(TypeError, Channel, name="newchan", data=numbs) def test_cmp(self): """Comparison of channels. """ self.chan = Channel(name="newchan") self.chan2 = Channel(name="mychan") self.assertTrue(self.chan > self.chan2) self.chan = Channel(name="newchan") self.chan2 = "mychan" self.assertTrue(self.chan > self.chan2) self.chan = Channel(name="newchan") self.chan2 = Channel(name="newchan") self.assert_(self.chan == self.chan2) self.chan = Channel(wavelength_range=(1., 2., 3.)) self.chan2 = Channel(name="newchan") self.assert_(self.chan < self.chan2) self.chan = Channel(name="newchan") self.chan2 = Channel(name="_mychan") self.assert_(self.chan < self.chan2) self.chan = Channel(name="_newchan") self.chan2 = Channel(name="mychan") self.assert_(self.chan > self.chan2) self.chan = Channel(name=random_string(4), wavelength_range=(1., 2., 3.)) self.chan2 = Channel(name=random_string(4), wavelength_range=(4., 5., 6.)) self.assert_(self.chan < self.chan2) self.chan = Channel(name="_" + random_string(4), wavelength_range=(1., 2., 3.)) self.chan2 = Channel(name=random_string(4), wavelength_range=(4., 5., 6.)) self.assert_(self.chan > self.chan2) def test_str(self): """String output for a channel. """ self.chan = Channel(name="newchan", wavelength_range=(1., 2., 3.), resolution=1000) self.assertEqual( str(self.chan), "'newchan: (1.000,2.000,3.000)μm, resolution 1000m," " not loaded'") self.chan.data = np.random.rand(3, 3) self.assertEqual( str(self.chan), "'newchan: (1.000,2.000,3.000)μm, " "shape (3, 3), " "resolution 1000m'") def test_is_loaded(self): """Check load status of a channel. """ data = np.random.rand(3, 3) self.chan = Channel(name="newchan") self.assert_(not self.chan.is_loaded()) self.chan = Channel(name="newchan", data=data) self.assert_(self.chan.is_loaded()) def test_as_image(self): """Check the geo_image version of the channel. """ data = np.random.rand(3, 3) self.chan = Channel(name="newchan", data=data) img = self.chan.as_image(False) self.assert_(np.allclose(img.channels[0], data)) self.assertEqual(img.mode, "L") img = self.chan.as_image(True) self.assertEqual(img.channels[0].max(), 1) self.assertEqual(img.channels[0].min(), 0) def test_check_range(self): """Check the range of a channel. """ self.chan = Channel(name="newchan") self.assertRaises(ValueError, self.chan.check_range) numb = np.random.uniform(10) self.assertRaises(ValueError, self.chan.check_range, numb) # ndarray data = np.random.rand(3, 3) self.chan = Channel(name="newchan", data=data) min_range = (data.max() - data.min()) / 2 self.assert_(np.all(data == self.chan.check_range(min_range))) zeros = np.zeros_like(data) min_range = (data.max() - data.min()) + E self.assert_(np.all(zeros == self.chan.check_range(min_range))) # masked array mask = np.array(np.random.rand(3, 3) * 2, dtype=int) mask[1, 1] = False data = np.ma.array(data, mask=mask) self.chan = Channel(name="newchan", data=data) min_range = (data.max() - data.min()) / 2 self.assert_(np.all(data == self.chan.check_range(min_range))) self.assertEquals(data.count(), self.chan.check_range(min_range).count()) zeros = np.zeros_like(data) min_range = (data.max() - data.min()) + E self.assert_(np.all(zeros == self.chan.check_range(min_range))) data = np.ma.array(data, mask=True) self.chan = Channel(name="newchan", data=data) self.assertEquals(0, self.chan.check_range(min_range).count()) self.assertEquals(data.count(), self.chan.check_range(min_range).count()) # Wrong type arguments self.assertRaises(TypeError, self.chan.check_range, random_string(4)) self.assertRaises(TypeError, self.chan.check_range, [np.random.uniform()]) def test_sunzen_corr(self): '''Test Sun zenith angle correction. ''' import datetime as dt chan = Channel(name='test') original_value = 10. chan.data = original_value * np.ones((2, 11)) lats = np.zeros((2, 11)) # equator lons = np.array([np.linspace(-90, 90, 11), np.linspace(-90, 90, 11)]) # Equinox, so the Sun is at the equator time_slot = dt.datetime(2014, 3, 20, 16, 57) new_ch = chan.sunzen_corr(time_slot, lonlats=(lons, lats), limit=80.) # Test minimum after correction, accuracy of three decimals is enough #self.assertTrue(np.abs(10.000 - np.min(new_ch.data)) < 10**-3) self.assertAlmostEqual(10.000, np.min(new_ch.data), places=3) # Test maximum after correction self.assertAlmostEqual(57.588, np.max(new_ch.data), places=3) # There should be ten values at zenith angle >= 80 deg, and # these are all equal self.assertTrue(np.where(new_ch.data == \ np.max(new_ch.data))[0].shape[0] == 10) # All values should be larger than the starting values self.assertTrue(np.all(new_ch.data > original_value)) # Channel name self.assertEqual(new_ch.name, chan.name + '_SZC') # Test channel name in the info dict self.assertEqual(new_ch.name, chan.info['sun_zen_corrected']) # Test with several locations and arbitrary data chan = Channel(name='test2') chan.data = np.array( [[0., 67.31614275, 49.96271995, 99.41046645, 29.08660989], [87.61007584, 79.6683524, 53.20397351, 29.88260374, 62.33623915], [60.49283004, 54.04267222, 32.72365906, 91.44995651, 32.27232955], [63.71580638, 69.57673795, 7.63064373, 32.15683105, 9.05786335], [65.61434337, 33.2317155, 18.77672384, 30.13527574, 23.22572904]]) lons = np.array([[ 116.28695847, 164.1125604, 40.77223701, -113.54699788, 133.15558442 ], [-17.18990601, 75.17472034, 12.81618371, -40.75524952, 40.70898002], [ 42.74662341, 164.05671859, -166.58469404, -58.16684483, -144.97963063 ], [ 46.26303645, -167.48682034, 170.28131412, -17.80502488, -63.9031154 ], [ -107.14829679, -147.66665952, -0.75970554, 77.701768, -130.48677807 ]]) lats = np.array([ [-51.53681682, -83.21762788, 5.91008672, 22.51730385, 66.83356427], [82.78543163, 23.1529456, -7.16337152, -68.23118425, 28.72194953], [31.03440852, 70.55322517, -83.61780288, 29.88413938, 25.7214828], [-19.02517922, -19.20958728, -14.7825735, 22.66967876, 67.6089238], [45.12202477, 61.79674149, 58.71037615, -62.04350423, 13.06405864] ]) time_slot = dt.datetime(1998, 8, 1, 10, 0) # These are the expected results results = np.array([[ 0., 387.65821593, 51.74080022, 572.48205988, 138.96586013 ], [ 227.24857818, 105.53045776, 62.24134162, 172.0870564, 64.12902666 ], [ 63.08646652, 311.21934562, 188.44804188, 526.63931022, 185.84893885 ], [82.86856236, 400.6764648, 43.9431259, 46.58056343, 36.04457644], [ 377.85794388, 191.3738223, 27.55002934, 173.54213642, 133.75164285 ]]) new_ch = chan.sunzen_corr(time_slot, lonlats=(lons, lats), limit=80.) self.assertAlmostEqual(np.max(results - new_ch.data), 0.000, places=3)
class TestChannel(unittest.TestCase): """Class for testing the Channel class. """ chan = None chan2 = None def test_init(self): """Creation of a channel. """ self.assertRaises(ValueError, Channel) # Name self.chan = Channel(name="newchan") self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, 0) self.assert_(self.chan.data is None) numb = int(np.random.uniform(100000)) self.assertRaises(TypeError, Channel, name=numb) numb = np.random.uniform() * 100000 self.assertRaises(TypeError, Channel, name=numb) # Resolution numb = int(np.random.uniform(100000)) self.assertRaises(ValueError, Channel, resolution=numb) numb = int(np.random.uniform(100000)) self.chan = Channel(name="newchan", resolution=numb) self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, numb) self.assert_(self.chan.data is None) self.assertRaises(TypeError, Channel, name="newchan", resolution="a") # Wavelength numbs = [np.random.uniform(100), np.random.uniform(100), np.random.uniform(100)] numbs.sort() self.chan = Channel(wavelength_range=numbs) self.assertEqual(self.chan.name, None) self.assertEqual(self.chan.wavelength_range, numbs) self.assertEqual(self.chan.resolution, 0) self.assert_(self.chan.data is None) self.assertRaises(TypeError, Channel, wavelength_range=numbs[0:1]) numbs.sort(reverse=True) self.assertRaises(ValueError, Channel, wavelength_range=numbs) numbs = [int(np.random.uniform(100)), int(np.random.uniform(100)), int(np.random.uniform(100))] numbs.sort() self.assertRaises(TypeError, Channel, wavelength_range=numbs) self.assertRaises(TypeError, Channel, wavelength_range=random_string(4)) numb = np.random.uniform(100000) self.assertRaises(TypeError, Channel, wavelength_range=numb) numb = int(np.random.uniform(100000)) self.assertRaises(TypeError, Channel, wavelength_range=numb) # Data data = np.random.rand(3, 3) self.assertRaises(ValueError, Channel, data=data) self.chan = Channel(name="newchan", data=data) self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, 0) self.assert_(np.all(self.chan.data == data)) mask = np.array(np.random.rand(3, 3) * 2, dtype=int) data = np.ma.array(data, mask=mask) self.chan = Channel(name="newchan", data=data) self.assertEqual(self.chan.name, "newchan") self.assertEqual(self.chan.wavelength_range, [-np.inf, -np.inf, -np.inf]) self.assertEqual(self.chan.resolution, 0) self.assert_(np.all(self.chan.data == data)) self.assertRaises(TypeError, Channel, name="newchan", data=random_string(4)) numb = np.random.uniform(100000) self.assertRaises(TypeError, Channel, name="newchan", data=numb) numb = int(np.random.uniform(100000)) self.assertRaises(TypeError, Channel, name="newchan", data=numb) numbs = [np.random.uniform(100), np.random.uniform(100), np.random.uniform(100)] self.assertRaises(TypeError, Channel, name="newchan", data=numbs) def test_cmp(self): """Comparison of channels. """ self.chan = Channel(name="newchan") self.chan2 = Channel(name="mychan") self.assertTrue(self.chan > self.chan2) self.chan = Channel(name="newchan") self.chan2 = "mychan" self.assertTrue(self.chan > self.chan2) self.chan = Channel(name="newchan") self.chan2 = Channel(name="newchan") self.assert_(self.chan == self.chan2) self.chan = Channel(wavelength_range=(1.0, 2.0, 3.0)) self.chan2 = Channel(name="newchan") self.assert_(self.chan < self.chan2) self.chan = Channel(name="newchan") self.chan2 = Channel(name="_mychan") self.assert_(self.chan < self.chan2) self.chan = Channel(name="_newchan") self.chan2 = Channel(name="mychan") self.assert_(self.chan > self.chan2) self.chan = Channel(name=random_string(4), wavelength_range=(1.0, 2.0, 3.0)) self.chan2 = Channel(name=random_string(4), wavelength_range=(4.0, 5.0, 6.0)) self.assert_(self.chan < self.chan2) self.chan = Channel(name="_" + random_string(4), wavelength_range=(1.0, 2.0, 3.0)) self.chan2 = Channel(name=random_string(4), wavelength_range=(4.0, 5.0, 6.0)) self.assert_(self.chan > self.chan2) def test_str(self): """String output for a channel. """ self.chan = Channel(name="newchan", wavelength_range=(1.0, 2.0, 3.0), resolution=1000) self.assertEqual(str(self.chan), "'newchan: (1.000,2.000,3.000)μm, resolution 1000m," " not loaded'") self.chan.data = np.random.rand(3, 3) self.assertEqual(str(self.chan), "'newchan: (1.000,2.000,3.000)μm, " "shape (3, 3), " "resolution 1000m'") def test_is_loaded(self): """Check load status of a channel. """ data = np.random.rand(3, 3) self.chan = Channel(name="newchan") self.assert_(not self.chan.is_loaded()) self.chan = Channel(name="newchan", data=data) self.assert_(self.chan.is_loaded()) def test_as_image(self): """Check the geo_image version of the channel. """ data = np.random.rand(3, 3) self.chan = Channel(name="newchan", data=data) img = self.chan.as_image(False) self.assert_(np.allclose(img.channels[0], data)) self.assertEqual(img.mode, "L") img = self.chan.as_image(True) self.assertEqual(img.channels[0].max(), 1) self.assertEqual(img.channels[0].min(), 0) def test_check_range(self): """Check the range of a channel. """ self.chan = Channel(name="newchan") self.assertRaises(ValueError, self.chan.check_range) numb = np.random.uniform(10) self.assertRaises(ValueError, self.chan.check_range, numb) # ndarray data = np.random.rand(3, 3) self.chan = Channel(name="newchan", data=data) min_range = (data.max() - data.min()) / 2 self.assert_(np.all(data == self.chan.check_range(min_range))) zeros = np.zeros_like(data) min_range = (data.max() - data.min()) + E self.assert_(np.all(zeros == self.chan.check_range(min_range))) # masked array mask = np.array(np.random.rand(3, 3) * 2, dtype=int) mask[1, 1] = False data = np.ma.array(data, mask=mask) self.chan = Channel(name="newchan", data=data) min_range = (data.max() - data.min()) / 2 self.assert_(np.all(data == self.chan.check_range(min_range))) self.assertEquals(data.count(), self.chan.check_range(min_range).count()) zeros = np.zeros_like(data) min_range = (data.max() - data.min()) + E self.assert_(np.all(zeros == self.chan.check_range(min_range))) data = np.ma.array(data, mask=True) self.chan = Channel(name="newchan", data=data) self.assertEquals(0, self.chan.check_range(min_range).count()) self.assertEquals(data.count(), self.chan.check_range(min_range).count()) # Wrong type arguments self.assertRaises(TypeError, self.chan.check_range, random_string(4)) self.assertRaises(TypeError, self.chan.check_range, [np.random.uniform()]) def test_sunzen_corr(self): """Test Sun zenith angle correction. """ import datetime as dt chan = Channel(name="test") original_value = 10.0 chan.data = original_value * np.ones((2, 11)) lats = np.zeros((2, 11)) # equator lons = np.array([np.linspace(-90, 90, 11), np.linspace(-90, 90, 11)]) # Equinox, so the Sun is at the equator time_slot = dt.datetime(2014, 3, 20, 16, 57) new_ch = chan.sunzen_corr(time_slot, lonlats=(lons, lats), limit=80.0) # Test minimum after correction, accuracy of three decimals is enough # self.assertTrue(np.abs(10.000 - np.min(new_ch.data)) < 10**-3) self.assertAlmostEqual(10.000, np.min(new_ch.data), places=3) # Test maximum after correction self.assertAlmostEqual(57.588, np.max(new_ch.data), places=3) # There should be ten values at zenith angle >= 80 deg, and # these are all equal self.assertTrue(np.where(new_ch.data == np.max(new_ch.data))[0].shape[0] == 10) # All values should be larger than the starting values self.assertTrue(np.all(new_ch.data > original_value)) # Channel name self.assertEqual(new_ch.name, chan.name + "_SZC") # Test channel name in the info dict self.assertEqual(new_ch.name, chan.info["sun_zen_corrected"]) # Test with several locations and arbitrary data chan = Channel(name="test2") chan.data = np.array( [ [0.0, 67.31614275, 49.96271995, 99.41046645, 29.08660989], [87.61007584, 79.6683524, 53.20397351, 29.88260374, 62.33623915], [60.49283004, 54.04267222, 32.72365906, 91.44995651, 32.27232955], [63.71580638, 69.57673795, 7.63064373, 32.15683105, 9.05786335], [65.61434337, 33.2317155, 18.77672384, 30.13527574, 23.22572904], ] ) lons = np.array( [ [116.28695847, 164.1125604, 40.77223701, -113.54699788, 133.15558442], [-17.18990601, 75.17472034, 12.81618371, -40.75524952, 40.70898002], [42.74662341, 164.05671859, -166.58469404, -58.16684483, -144.97963063], [46.26303645, -167.48682034, 170.28131412, -17.80502488, -63.9031154], [-107.14829679, -147.66665952, -0.75970554, 77.701768, -130.48677807], ] ) lats = np.array( [ [-51.53681682, -83.21762788, 5.91008672, 22.51730385, 66.83356427], [82.78543163, 23.1529456, -7.16337152, -68.23118425, 28.72194953], [31.03440852, 70.55322517, -83.61780288, 29.88413938, 25.7214828], [-19.02517922, -19.20958728, -14.7825735, 22.66967876, 67.6089238], [45.12202477, 61.79674149, 58.71037615, -62.04350423, 13.06405864], ] ) time_slot = dt.datetime(1998, 8, 1, 10, 0) # These are the expected results results = np.array( [ [0.0, 387.65821593, 51.74080022, 572.48205988, 138.96586013], [227.24857818, 105.53045776, 62.24134162, 172.0870564, 64.12902666], [63.08646652, 311.21934562, 188.44804188, 526.63931022, 185.84893885], [82.86856236, 400.6764648, 43.9431259, 46.58056343, 36.04457644], [377.85794388, 191.3738223, 27.55002934, 173.54213642, 133.75164285], ] ) new_ch = chan.sunzen_corr(time_slot, lonlats=(lons, lats), limit=80.0) self.assertAlmostEqual(np.max(results - new_ch.data), 0.000, places=3)
def load_from_nc4(filename): """Load data from a netcdf4 file, cf-satellite v0.1 """ rootgrp = Dataset(filename, 'r') try: rootgrp.satellite_number warnings.warn("You are loading old style netcdf files...", DeprecationWarning) except AttributeError: return _load02(filename) if not isinstance(rootgrp.satellite_number, str): satellite_number = "%02d" % rootgrp.satellite_number else: satellite_number = str(rootgrp.satellite_number) time_slot = rootgrp.variables["time"].getValue()[0] time_slot = num2date(time_slot, TIME_UNITS) service = str(rootgrp.service) satellite_name = str(rootgrp.satellite_name) instrument_name = str(rootgrp.instrument_name) try: orbit = str(rootgrp.orbit) except AttributeError: orbit = None try: scene = GenericFactory.create_scene(satellite_name, satellite_number, instrument_name, time_slot, orbit, None, service) except NoSectionError: scene = VisirCompositer(time_slot=time_slot) scene.satname = satellite_name scene.number = satellite_number scene.service = service for var_name, var in rootgrp.variables.items(): area = None if var_name.startswith("band_data"): resolution = var.resolution str_res = str(int(resolution)) + "m" names = rootgrp.variables["bandname"+str_res][:] data = var[:, :, :].astype(var.dtype) data = np.ma.masked_outside(data, var.valid_range[0], var.valid_range[1]) try: area_var = getattr(var,"grid_mapping") area_var = rootgrp.variables[area_var] proj4_dict = {} for attr, projattr in MAPPING_ATTRIBUTES.items(): try: the_attr = getattr(area_var, attr) if projattr == "proj": proj4_dict[projattr] = PROJNAME[the_attr] elif(isinstance(projattr, (list, tuple))): try: for i, subattr in enumerate(the_attr): proj4_dict[projattr[i]] = subattr except TypeError: proj4_dict[projattr[0]] = the_attr else: proj4_dict[projattr] = the_attr except AttributeError: pass x__ = rootgrp.variables["x"+str_res][:] y__ = rootgrp.variables["y"+str_res][:] x_pixel_size = abs((x__[1] - x__[0])) y_pixel_size = abs((y__[1] - y__[0])) llx = x__[0] - x_pixel_size / 2.0 lly = y__[-1] - y_pixel_size / 2.0 urx = x__[-1] + x_pixel_size / 2.0 ury = y__[0] + y_pixel_size / 2.0 area_extent = (llx, lly, urx, ury) try: # create the pyresample areadef from pyresample.geometry import AreaDefinition area = AreaDefinition("myareaid", "myareaname", "myprojid", proj4_dict, data.shape[1], data.shape[0], area_extent) except ImportError: LOG.warning("Pyresample not found, " "cannot load area descrition") except AttributeError: LOG.debug("No grid mapping found.") try: area_var = getattr(var,"coordinates") coordinates_vars = area_var.split(" ") lons = None lats = None for coord_var_name in coordinates_vars: coord_var = rootgrp.variables[coord_var_name] units = getattr(coord_var, "units") if(coord_var_name.lower().startswith("lon") or units.lower().endswith("east") or units.lower().endswith("west")): lons = coord_var[:] elif(coord_var_name.lower().startswith("lat") or units.lower().endswith("north") or units.lower().endswith("south")): lats = coord_var[:] if lons and lats: try: from pyresample.geometry import SwathDefinition area = SwathDefinition(lons=lons, lats=lats) except ImportError: LOG.warning("Pyresample not found, " "cannot load area descrition") except AttributeError: LOG.debug("No lon/lat found.") for i, name in enumerate(names): name = str(name) if var.dimensions[0].startswith("band"): chn_data = data[i, :, :] elif var.dimensions[1].startswith("band"): chn_data = data[:, i, :] elif var.dimensions[2].startswith("band"): chn_data = data[:, :, i] else: raise ValueError("Invalid dimension names for band data") try: scene[name] = (chn_data * rootgrp.variables["scale"+str_res][i] + rootgrp.variables["offset"+str_res][i]) #FIXME complete this #scene[name].info except KeyError: # build the channel on the fly from satpy.channel import Channel wv_var = rootgrp.variables["nominal_wavelength"+str_res] wb_var = rootgrp.variables[getattr(wv_var, "bounds")] minmax = wb_var[i] scene.channels.append(Channel(name, resolution, (minmax[0], wv_var[i][0], minmax[1]))) scene[name] = (chn_data * rootgrp.variables["scale"+str_res][i] + rootgrp.variables["offset"+str_res][i]) if area is not None: scene[name].area = area area = None for attr in rootgrp.ncattrs(): scene.info[attr] = getattr(rootgrp, attr) scene.add_to_history("Loaded from netcdf4/cf by satpy") return scene