/[thuban]/branches/WIP-pyshapelib-bramz/Thuban/Model/data.py
ViewVC logotype

Contents of /branches/WIP-pyshapelib-bramz/Thuban/Model/data.py

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1535 - (show annotations)
Fri Aug 1 14:27:13 2003 UTC (21 years, 7 months ago) by bh
Original Path: trunk/thuban/Thuban/Model/data.py
File MIME type: text/x-python
File size: 7708 byte(s)
* Thuban/Model/data.py (SHAPETYPE_POLYGON, SHAPETYPE_ARC)
(SHAPETYPE_POINT, Shape): Move these constants and classes from
layer.py to data.py
(ShapefileStore.__init__): More Initialization for the new methods
and functionality.
(ShapefileStore.ShapeType, ShapefileStore.NumShapes)
(ShapefileStore.BoundingBox, ShapefileStore.ShapesInRegion)
(ShapefileStore.Shape): New methods that were formerly implemented
in the layer.
(DerivedShapeStore.Shape, DerivedShapeStore.ShapesInRegion)
(DerivedShapeStore.ShapeType, DerivedShapeStore.NumShapes)
(DerivedShapeStore.BoundingBox): New. DerivedShapeStore
equivalents of the new shape methods. These versions are simply
delegated to the original shapstore.

* Thuban/Model/layer.py (SHAPETYPE_POLYGON, SHAPETYPE_ARC)
(SHAPETYPE_POINT, Shape): Removed. They're now in data.py
(Layer.SetShapeStore): Removed the initializatin of instance
variables that were needed for the stuff that's now in
ShapefileStore
(Layer.BoundingBox, Layer.NumShapes, Layer.ShapeType)
(Layer.Shape, Layer.ShapesInRegion): Simply delegate to the
shapestore.

1 # Copyright (C) 2003 by Intevation GmbH
2 # Authors:
3 # Bernhard Herzog <[email protected]>
4 #
5 # This program is free software under the GPL (>=v2)
6 # Read the file COPYING coming with the software for details.
7
8 """Data source abstractions"""
9
10 __version__ = "$Revision$"
11 # $Source$
12 # $Id$
13
14 import os
15 import weakref
16 from math import ceil, log
17
18 import shapelib
19 import shptree
20 import table
21 import transientdb
22
23 from Thuban import _
24
25 # Shape type constants
26 SHAPETYPE_POLYGON = "polygon"
27 SHAPETYPE_ARC = "arc"
28 SHAPETYPE_POINT = "point"
29
30 # mapping from shapelib shapetype constants to our constants
31 shapelib_shapetypes = {shapelib.SHPT_POLYGON: SHAPETYPE_POLYGON,
32 shapelib.SHPT_ARC: SHAPETYPE_ARC,
33 shapelib.SHPT_POINT: SHAPETYPE_POINT}
34
35
36 class Shape:
37
38 """Represent one shape"""
39
40 def __init__(self, points):
41 self.points = points
42 #self.compute_bbox()
43 self.bbox = None
44
45 def compute_bbox(self):
46 if self.bbox is not None:
47 return self.bbox
48
49 xs = []
50 ys = []
51 for x, y in self.points:
52 xs.append(x)
53 ys.append(y)
54 self.llx = min(xs)
55 self.lly = min(ys)
56 self.urx = max(xs)
57 self.ury = max(ys)
58
59 self.bbox = (self.llx, self.lly, self.urx, self.ury)
60
61 return self.bbox
62
63 def Points(self):
64 return self.points
65
66
67
68 class ShapeTable(transientdb.AutoTransientTable):
69
70 """A Table that depends on a ShapefileStore
71
72 Intended use is by the ShapefileStore for the table associated with
73 the shapefiles.
74 """
75
76 def __init__(self, store, db, table):
77 """Initialize the ShapeTable.
78
79 Parameters:
80 store -- the ShapefileStore the table is to depend on
81 db -- The transient database to use
82 table -- the table
83 """
84 transientdb.AutoTransientTable.__init__(self, db, table)
85 self.store = weakref.ref(store)
86
87 def Dependencies(self):
88 """Return a tuple containing the shapestore"""
89 return (self.store(),)
90
91
92 class ShapefileStore:
93
94 """Combine a shapefile and the corresponding DBF file into one object"""
95
96 def __init__(self, session, filename):
97 # Make the filename absolute. The filename will be
98 # interpreted relative to that anyway, but when saving a
99 # session we need to compare absolute paths and it's usually
100 # safer to always work with absolute paths.
101 self.filename = os.path.abspath(filename)
102
103 self.shapefile = shapelib.ShapeFile(self.filename)
104 self.dbftable = table.DBFTable(filename)
105 self.table = ShapeTable(self, session.TransientDB(), self.dbftable)
106
107 self.numshapes, shapetype, mins, maxs = self.shapefile.info()
108 if self.numshapes:
109 self.bbox = mins[:2] + maxs[:2]
110 else:
111 self.bbox = None
112 self.shapetype = shapelib_shapetypes[shapetype]
113
114 # estimate a good depth for the quad tree. Each depth multiplies
115 # the number of nodes by four, therefore we basically take the
116 # base 4 logarithm of the number of shapes.
117 if self.numshapes < 4:
118 maxdepth = 1
119 else:
120 maxdepth = int(ceil(log(self.numshapes / 4.0) / log(4)))
121
122 self.shapetree = shptree.SHPTree(self.shapefile.cobject(), 2,
123 maxdepth)
124
125 def Table(self):
126 """Return the table containing the attribute data"""
127 return self.table
128
129 def Shapefile(self):
130 """Return the shapefile object"""
131 return self.shapefile
132
133 def FileName(self):
134 """Return the filename used to open the shapefile"""
135 return self.filename
136
137 def FileType(self):
138 """Return the filetype. This is always the string 'shapefile'"""
139 return "shapefile"
140
141 def ShapeType(self):
142 """Return the type of the shapes in the shapestore.
143
144 This is either SHAPETYPE_POINT, SHAPETYPE_ARC or SHAPETYPE_POLYGON.
145 """
146 return self.shapetype
147
148 def NumShapes(self):
149 """Return the number of shapes in the shape store"""
150 return self.numshapes
151
152 def Dependencies(self):
153 """Return the empty tuple.
154
155 The ShapefileStore doesn't depend on anything else.
156 """
157 return ()
158
159 def OrigShapeStore(self):
160 """Return None.
161
162 The ShapefileStore was not derived from another shapestore.
163 """
164 return None
165
166 def BoundingBox(self):
167 """Return the bounding box of the shapes in the shapestore.
168
169 The coordinate system used is whatever was used in the shapefile.
170 If the shapefile is empty, return None.
171 """
172 return self.bbox
173
174 def ShapesInRegion(self, box):
175 """Return the ids of the shapes that overlap the box.
176
177 Box is a tuple (left, bottom, right, top) in the coordinate
178 system used used in the shapefile.
179 """
180 left, bottom, right, top = box
181 return self.shapetree.find_shapes((left, bottom), (right, top))
182
183 def Shape(self, index):
184 """Return the shape with index index"""
185 shape = self.shapefile.read_object(index)
186
187 if self.ShapeType() == SHAPETYPE_POINT:
188 points = shape.vertices()
189 else:
190 #for poly in shape.vertices():
191 poly = shape.vertices()[0]
192 points = []
193 for x, y in poly:
194 points.append((x, y))
195
196 return Shape(points)
197
198
199
200 class DerivedShapeStore:
201
202 """A ShapeStore derived from other shapestores or tables"""
203
204 def __init__(self, shapestore, table):
205 """Initialize the derived shapestore.
206
207 The arguments are a shapestore for the shapedata and a table for
208 the tabular data.
209
210 Raises ValueError if the number of shapes in the shapestore
211 is different from the number of rows in the table.
212 """
213
214 numShapes = shapestore.Shapefile().info()[0]
215 if numShapes != table.NumRows():
216 raise ValueError(_("Table not compatible with shapestore."))
217
218 self.shapestore = shapestore
219 self.table = table
220
221 def Table(self):
222 """Return the table"""
223 return self.table
224
225 def Shapefile(self):
226 """Return the shapefile of the underlying shapestore"""
227 return self.shapestore.Shapefile()
228
229 def Dependencies(self):
230 """Return a tuple containing the shapestore and the table"""
231 return (self.shapestore, self.table)
232
233 def OrigShapeStore(self):
234 """
235 Return the original shapestore the derived store was instantiated with
236 """
237 return self.shapestore
238
239 def Shape(self, index):
240 """Return the shape with index index"""
241 return self.shapestore.Shape(index)
242
243 def ShapesInRegion(self, bbox):
244 """Return the ids of the shapes that overlap the box.
245
246 This method is simply delegated to the shapestore the
247 DerivedShapeStore was instantiated with.
248 """
249 return self.shapestore.ShapesInRegion(bbox)
250
251 def ShapeType(self):
252 """Return the type of the shapes in the layer.
253
254 This method is simply delegated to the shapestore the
255 DerivedShapeStore was instantiated with.
256 """
257 return self.shapestore.ShapeType()
258
259 def NumShapes(self):
260 """Return the number of shapes in the shapestore."""
261 return self.shapestore.NumShapes()
262
263 def BoundingBox(self):
264 """Return the bounding box of the shapes in the shapestore.
265
266 This method is simply delegated to the shapestore the
267 DerivedShapeStore was instantiated with.
268 """
269 return self.shapestore.BoundingBox()

Properties

Name Value
svn:eol-style native
svn:keywords Author Date Id Revision

[email protected]
ViewVC Help
Powered by ViewVC 1.1.26