Commit c485e672 authored by Hoek, Steven's avatar Hoek, Steven
Browse files

Initialisation and tiling

In the classes from the formats folder better initialisation was implemented. The Tile manager in module tilelib was improved too.
parent b1434a19
...@@ -37,7 +37,8 @@ class AsciiGrid(Raster, GridEnvelope2D): ...@@ -37,7 +37,8 @@ class AsciiGrid(Raster, GridEnvelope2D):
self.name = "dummy." + self._const.FILEXT; self.name = "dummy." + self._const.FILEXT;
# Initialise further # Initialise further
super(AsciiGrid, self).__init__(filepath) Raster.__init__(self, filepath)
GridEnvelope2D.__init__(self, 1, 1, 0.0, 0.0, 0.1, 0.1)
# Retrieve the name from the filepath and assign - incl. extension # Retrieve the name from the filepath and assign - incl. extension
self.name = os.path.basename(filepath); self.name = os.path.basename(filepath);
......
...@@ -28,6 +28,8 @@ class BandRaster(Raster, GridEnvelope2D): ...@@ -28,6 +28,8 @@ class BandRaster(Raster, GridEnvelope2D):
# Initialise # Initialise
Raster.__init__(self, filepath) Raster.__init__(self, filepath)
GridEnvelope2D.__init__(self, 1, 1, 0.0, 0.0, 0.1, 0.1)
# Retrieve the name from the filepath and assign - incl. extension # Retrieve the name from the filepath and assign - incl. extension
self.name = os.path.basename(filepath); self.name = os.path.basename(filepath);
# Also derive the folder # Also derive the folder
......
...@@ -31,7 +31,7 @@ class BaseTiffRaster(Raster): ...@@ -31,7 +31,7 @@ class BaseTiffRaster(Raster):
print('File path cannot be an empty string (method __init__).') print('File path cannot be an empty string (method __init__).')
# Initialise # Initialise
super(BaseTiffRaster, self).__init__(filepath) Raster.__init__(self, filepath)
# Module wide constants # Module wide constants
self._const = Const() self._const = Const()
......
...@@ -64,7 +64,10 @@ class BitmapRaster(Raster, GridEnvelope2D): ...@@ -64,7 +64,10 @@ class BitmapRaster(Raster, GridEnvelope2D):
# Module wide constants # Module wide constants
self._const = Const() self._const = Const()
self._const.FILEXT = "bmp" self._const.FILEXT = "bmp"
super(BitmapRaster, self).__init__(filepath)
# Initialise further
Raster.__init__(self, filepath)
GridEnvelope2D.__init__(self, 1, 1, 0.0, 0.0, 0.1, 0.1)
# Retrieve the name from the filepath and assign - incl. extension; idem folder # Retrieve the name from the filepath and assign - incl. extension; idem folder
self.name = os.path.basename(filepath); self.name = os.path.basename(filepath);
......
...@@ -197,7 +197,10 @@ class CsfRaster(Raster, GridEnvelope2D): ...@@ -197,7 +197,10 @@ class CsfRaster(Raster, GridEnvelope2D):
# Module wide constants # Module wide constants
self._const = Const() self._const = Const()
self._const.FILEXT = "map" self._const.FILEXT = "map"
super(CsfRaster, self).__init__(filepath)
# Initialise further
Raster.__init__(self, filepath)
GridEnvelope2D.__init__(self, 1, 1, 0.0, 0.0, 0.1, 0.1)
# Retrieve the name from the filepath and assign - incl. extension; idem folder # Retrieve the name from the filepath and assign - incl. extension; idem folder
self.name = os.path.basename(filepath); self.name = os.path.basename(filepath);
......
...@@ -32,6 +32,7 @@ class FloatingPointRaster(Raster, GridEnvelope2D): ...@@ -32,6 +32,7 @@ class FloatingPointRaster(Raster, GridEnvelope2D):
# Initialise # Initialise
Raster.__init__(self, filepath) Raster.__init__(self, filepath)
GridEnvelope2D.__init__(self, 1, 1, 0.0, 0.0, 0.1, 0.1)
self._const = Const() self._const = Const()
# Class and subclass wide constants # Class and subclass wide constants
......
...@@ -41,6 +41,10 @@ class GeotiffRaster(Raster, GridEnvelope2D): ...@@ -41,6 +41,10 @@ class GeotiffRaster(Raster, GridEnvelope2D):
__memmap = None; __memmap = None;
def __init__(self, filepath, *datatype): def __init__(self, filepath, *datatype):
# Initialise
Raster.__init__(self, filepath)
GridEnvelope2D.__init__(self, 1, 1, 0.0, 0.0, 0.1, 0.1)
# Retrieve the name from the filepath and assign - incl. extension # Retrieve the name from the filepath and assign - incl. extension
self.name = os.path.basename(filepath); self.name = os.path.basename(filepath);
# Also derive the folder # Also derive the folder
......
...@@ -39,8 +39,10 @@ class Hdf5Raster(Raster, GridEnvelope2D): ...@@ -39,8 +39,10 @@ class Hdf5Raster(Raster, GridEnvelope2D):
currow = 0; currow = 0;
def __init__(self, filepath): def __init__(self, filepath):
# Initialise super class instance # Initialise
Raster.__init__(self, filepath) Raster.__init__(self, filepath)
GridEnvelope2D.__init__(self, 1, 1, 0.0, 0.0, 0.1, 0.1)
# Retrieve the name from the filepath and assign - incl. extension # Retrieve the name from the filepath and assign - incl. extension
self.name = os.path.basename(filepath); self.name = os.path.basename(filepath);
# Also derive the folder # Also derive the folder
......
...@@ -18,7 +18,10 @@ class InMemoryRaster(Raster, GridEnvelope2D): ...@@ -18,7 +18,10 @@ class InMemoryRaster(Raster, GridEnvelope2D):
dataformat = 'f' dataformat = 'f'
def __init__(self, filepath, data=None, *datatype): def __init__(self, filepath, data=None, *datatype):
# Initialise
Raster.__init__(self, filepath) Raster.__init__(self, filepath)
GridEnvelope2D.__init__(self, 1, 1, 0.0, 0.0, 0.1, 0.1)
if not data is None: if not data is None:
self.data = data self.data = data
if len(datatype) > 0: if len(datatype) > 0:
......
...@@ -11,7 +11,7 @@ except ImportError: ...@@ -11,7 +11,7 @@ except ImportError:
__author__ = "Steven B. Hoek" __author__ = "Steven B. Hoek"
class Netcdf4Raster(Netcdf4Envelope2D): class Netcdf4Raster(Netcdf4Envelope2D):
# Constants # Constants
DATAFILEXT = 'nc4'; DATAFILEXT = 'nc4';
_original_name = "Band1" # TODO: set it when a template file is opened for appending _original_name = "Band1" # TODO: set it when a template file is opened for appending
...@@ -28,6 +28,9 @@ class Netcdf4Raster(Netcdf4Envelope2D): ...@@ -28,6 +28,9 @@ class Netcdf4Raster(Netcdf4Envelope2D):
__Y = "" __Y = ""
def __init__(self, filepath): def __init__(self, filepath):
# Initialise
Netcdf4Envelope2D.__init__(None)
# Retrieve the name from the filepath and assign - incl. extension # Retrieve the name from the filepath and assign - incl. extension
self.name = os.path.basename(filepath); self.name = os.path.basename(filepath);
# Also derive the folder # Also derive the folder
......
...@@ -24,6 +24,8 @@ class NumpyRaster(Raster, GridEnvelope2D): ...@@ -24,6 +24,8 @@ class NumpyRaster(Raster, GridEnvelope2D):
def __init__(self, filepath, *datatype): def __init__(self, filepath, *datatype):
# Initialise # Initialise
Raster.__init__(self, filepath) Raster.__init__(self, filepath)
GridEnvelope2D.__init__(self, 1, 1, 0.0, 0.0, 0.1, 0.1)
# Retrieve the name from the filepath and assign - incl. extension # Retrieve the name from the filepath and assign - incl. extension
self.name = os.path.basename(filepath) self.name = os.path.basename(filepath)
# Also derive the folder # Also derive the folder
......
...@@ -46,7 +46,8 @@ class RowTiffRaster(BaseTiffRaster, GridEnvelope2D): ...@@ -46,7 +46,8 @@ class RowTiffRaster(BaseTiffRaster, GridEnvelope2D):
print('File path cannot be an empty string (method __init__).') print('File path cannot be an empty string (method __init__).')
# Initialise # Initialise
super(RowTiffRaster, self).__init__(filepath) BaseTiffRaster.__init__(self, filepath)
GridEnvelope2D.__init__(self, 1, 1, 0.0, 0.0, 0.1, 0.1)
if self._const == None: if self._const == None:
raise AttributeError("TIFF raster not properly initialised!") raise AttributeError("TIFF raster not properly initialised!")
......
...@@ -42,7 +42,9 @@ class StripTiffRaster(BaseTiffRaster, GridEnvelope2D): ...@@ -42,7 +42,9 @@ class StripTiffRaster(BaseTiffRaster, GridEnvelope2D):
def __init__(self, filepath, *datatype): def __init__(self, filepath, *datatype):
# Initialise # Initialise
super(StripTiffRaster, self).__init__(filepath) BaseTiffRaster.__init__(filepath)
GridEnvelope2D.__init__(self, 1, 1, 0.0, 0.0, 0.1, 0.1)
# Retrieve the name from the filepath and assign - incl. extension # Retrieve the name from the filepath and assign - incl. extension
self.name = os.path.basename(filepath); self.name = os.path.basename(filepath);
# Also derive the folder # Also derive the folder
......
...@@ -41,7 +41,9 @@ class TileTiffRaster(BaseTiffRaster, GridEnvelope2D): ...@@ -41,7 +41,9 @@ class TileTiffRaster(BaseTiffRaster, GridEnvelope2D):
def __init__(self, filepath, *datatype): def __init__(self, filepath, *datatype):
# Initialise # Initialise
super(TileTiffRaster, self).__init__(filepath) BaseTiffRaster.__init__(filepath)
GridEnvelope2D.__init__(self, 1, 1, 0.0, 0.0, 0.1, 0.1)
if self._const == None: if self._const == None:
raise AttributeError("TIFF raster not properly initialised!") raise AttributeError("TIFF raster not properly initialised!")
......
from lmgeo.formats.rioraster import RioRaster
from .test_baseraster import TestBaseRaster
import unittest
__author__ = "Steven B. Hoek"
class TestRioRaster(TestBaseRaster):
# Load data from a pickle file and metadata from a header file
# Write the data to an AsciiGrid. Close and open teh file again for reading and check
test_class = RioRaster
int_extension = 'tif'
def suite():
""" This defines all the tests of a module"""
suite = unittest.TestSuite()
suite.addTest(unittest.makeSuite(TestRioRaster))
return suite
from lmgeo.formats.rowtiffraster import RowTiffRaster
from .test_baseraster import TestBaseRaster
import unittest
__author__ = "Steven B. Hoek"
class TestRowTifRaster(TestBaseRaster):
# Load data from a pickle file and metadata from a header file
# Write the data to an AsciiGrid. Close and open teh file again for reading and check
test_class = RowTiffRaster
int_extension = 'tif'
flt_extension = 'tif'
def suite():
""" This defines all the tests of a module"""
suite = unittest.TestSuite()
suite.addTest(unittest.makeSuite(TestRowTifRaster))
return suite
\ No newline at end of file
...@@ -6,9 +6,19 @@ from ..formats.raster import Raster ...@@ -6,9 +6,19 @@ from ..formats.raster import Raster
from ..formats.inmemoryraster import InMemoryRaster from ..formats.inmemoryraster import InMemoryRaster
from ..toolbox.striplib import StripManager from ..toolbox.striplib import StripManager
from ..formats.const import constants as const from ..formats.const import constants as const
from math import ceil
import numpy as np
__author__ = "Steven B. Hoek" __author__ = "Steven B. Hoek"
class Tile(InMemoryRaster):
rowidx = 0
colidx = 0
def __init__(self, filepath, data=None, *datatype):
# Initialise
InMemoryRaster.__init__(self, filepath, data, datatype)
class TileManager(): class TileManager():
''' '''
Class that retrieves enough rows of data from a given raster grid to obtain a strip Class that retrieves enough rows of data from a given raster grid to obtain a strip
...@@ -19,14 +29,23 @@ class TileManager(): ...@@ -19,14 +29,23 @@ class TileManager():
__depth = 1 __depth = 1
__width = 1 __width = 1
__curcol = 0 __curcol = 0
__rowidx = -1 # actually strip index
__colidx = -1
__curstrip = None __curstrip = None
__stripmanager = None __stripmanager = None
__rowoffset = 0 # row offset __rowoffset = 0 # row offset
__coloffset = 0 # column offset __coloffset = 0 # column offset
__rowoverlap = 0 __rowoverlap = 0
__coloverlap = 0 __coloverlap = 0
__add_edges = True
def __init__(self, rg, tilewidth, tileheight, coloverlap=0, rowoverlap=0): def __init__(self, rg, tilewidth, tileheight, coloverlap=0, rowoverlap=0, addedges=False):
'''
Initialisation of the tile manager with tile width and tile height. In addition, it can be
indicated whether there should be column and row overlap should be and if so how many pixels.
In addition, it can be indicated whether edges with nodata should be added - or not - to the
tiles in order to make sures all delivered tiles are of the same width and height.
'''
# Check the inputs # Check the inputs
if not isinstance(rg, Raster): if not isinstance(rg, Raster):
raise TypeError("Input is not a raster!") raise TypeError("Input is not a raster!")
...@@ -40,13 +59,13 @@ class TileManager(): ...@@ -40,13 +59,13 @@ class TileManager():
self.__ncols = rg.ncols self.__ncols = rg.ncols
self.__nrows = rg.nrows self.__nrows = rg.nrows
self.__datatype = rg.datatype self.__datatype = rg.datatype
self.__curcol = 0
self.__stripmanager = StripManager(rg, tileheight) self.__stripmanager = StripManager(rg, tileheight)
self.__stripmanager.stripheight = tileheight self.__stripmanager.stripheight = tileheight
self.__depth = tileheight self.__depth = tileheight
self.__width = tilewidth self.__width = tilewidth
self.__rowoverlap = rowoverlap self.__rowoverlap = rowoverlap
self.__coloverlap = coloverlap self.__coloverlap = coloverlap
self.__addedges = addedges
# Get the first strip ready # Get the first strip ready
self.nextstrip() self.nextstrip()
...@@ -58,20 +77,48 @@ class TileManager(): ...@@ -58,20 +77,48 @@ class TileManager():
'''Returns a tile with number of rows and columns''' '''Returns a tile with number of rows and columns'''
# TODO: implement the option to have row and column offsets # TODO: implement the option to have row and column offsets
result = None result = None
if self.__curcol + self.__width > self.__ncols: maxrowno = self.__nrows // self.__depth # zero-based
width = self.__ncols - self.__curcol colsleft = self.__ncols - self.__curcol
else: if colsleft > self.__width:
# More tiles to be written
width = self.__width width = self.__width
if (width > 0) and (not self.__curstrip is None): else:
# Last tile of this strip
width = colsleft
if (colsleft > 0) and (not self.__curstrip is None):
# In case buffer contains rows, prepare to add them at the beginning of the output raster # In case buffer contains rows, prepare to add them at the beginning of the output raster
width += self.__coloverlap if self.__curcol + width + self.__coloverlap <= self.__ncols:
xll = self.__xll + (self.__curcol * self.__rg.dx) width += self.__coloverlap
data = self.__curstrip.data[:, self.__curcol:self.__curcol+width] data = self.__curstrip.data[:, self.__curcol:self.__curcol + width]
imr = InMemoryRaster("dummy_file.ext", data, self.__datatype)
width = min(width, len(data[0])) # Check whether extra columns have to be added
if (data.shape[1] < self.__width + self.__coloverlap) and self.__addedges:
extradata = np.empty((data.shape[0], self.__width + self.__coloverlap - data.shape[1]), dtype=data.dtype)
extradata.fill(self.__rg.nodatavalue)
data = np.append(data, extradata, 1)
# Establish width, height and the coordinates of the lower left point
width = data.shape[1]
height = self.__curstrip.nrows height = self.__curstrip.nrows
imr.open('w', width, height, xll, self.__yll, self.__rg.dy, self.__rg.nodatavalue) xll = self.__xll + (self.__curcol * self.__rg.dx)
yll = self.__curstrip.yll
# Check whether extra rows have to be added
if (self.__rowidx == maxrowno) and (height < self.__depth) and self.__addedges:
extradata = np.empty((self.__depth - height + self.__rowoverlap, data.shape[1]), dtype=data.dtype)
extradata.fill(self.__rg.nodatavalue)
data = np.append(data, extradata, 0)
yll = yll - (self.__depth - height + self.__rowoverlap) * self.__rg.dy
height = self.__depth + self.__rowoverlap
# Now that we have retrieved enough particulars, prepare the result
imr = Tile("dummy_file.ext", data, self.__datatype)
imr.open('w', width, height, xll, yll, self.__rg.dy, self.__rg.nodatavalue)
self.__curcol += self.__width self.__curcol += self.__width
self.__colidx += 1
imr.rowidx = self.__rowidx
imr.colidx = self.__colidx
result = imr result = imr
return result return result
...@@ -85,6 +132,8 @@ class TileManager(): ...@@ -85,6 +132,8 @@ class TileManager():
rowbuf = self.__curstrip.data[-1 * self.__rowoverlap:, :] rowbuf = self.__curstrip.data[-1 * self.__rowoverlap:, :]
self.__curstrip = self.__stripmanager.next(rowbuf, self.__rowoverlap) self.__curstrip = self.__stripmanager.next(rowbuf, self.__rowoverlap)
self.__curcol = 0 self.__curcol = 0
self.__colidx = -1
self.__rowidx += 1
result = True result = True
except: except:
raise StopIteration raise StopIteration
...@@ -154,7 +203,7 @@ class TileIterator: ...@@ -154,7 +203,7 @@ class TileIterator:
curcol = self.__tilemanager.curcol curcol = self.__tilemanager.curcol
width = self.__tilemanager.tilewidth width = self.__tilemanager.tilewidth
ncols = self.__tilemanager.ncols ncols = self.__tilemanager.ncols
tilesleft = (ncols - curcol) // width tilesleft = ceil((ncols - curcol) / width)
if tilesleft > 0: if tilesleft > 0:
result = self.__tilemanager.next() result = self.__tilemanager.next()
else: else:
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment