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

Annotation of /branches/WIP-pyshapelib-bramz/Thuban/Model/load.py

Parent Directory Parent Directory | Revision Log Revision Log


Revision 413 - (hide annotations)
Wed Feb 19 16:52:04 2003 UTC (22 years ago) by jonathan
Original Path: trunk/thuban/Thuban/Model/load.py
File MIME type: text/x-python
File size: 9191 byte(s)
(ProcessSession): Use new methods on Layer
        to get the classifcation and use the new ClassData* classes to
        hold the classification data. Use Str2Num to convert numbers
        properly.

1 bh 75 # Copyright (C) 2001, 2002 by Intevation GmbH
2 bh 6 # Authors:
3     # Jan-Oliver Wagner <[email protected]>
4 bh 267 # Bernhard Herzog <[email protected]>
5 jonathan 413 # Jonathan Coles <[email protected]>
6 bh 6 #
7     # This program is free software under the GPL (>=v2)
8     # Read the file COPYING coming with GRASS for details.
9    
10     """
11     Parser for thuban session files.
12     """
13    
14     __version__ = "$Revision$"
15    
16     import sys, string, os
17 bh 267
18     import xml.sax
19     import xml.sax.handler
20     from xml.sax import make_parser, ErrorHandler
21    
22 jan 374 from Thuban import _
23 jonathan 413 from Thuban.common import *
24    
25 bh 6 from Thuban.Model.session import Session
26     from Thuban.Model.map import Map
27     from Thuban.Model.layer import Layer
28     from Thuban.Model.color import Color
29     from Thuban.Model.proj import Projection
30 jonathan 413 from Thuban.Model.classification import Classification, \
31     ClassDataDefault, ClassDataPoint, ClassDataRange, ClassDataMap
32 bh 6
33    
34 bh 267 def parse_color(color):
35     """Return the color object for the string color.
36 bh 6
37 bh 267 Color may be either 'None' or of the form '#RRGGBB' in the usual
38     HTML color notation
39 bh 6 """
40     color = string.strip(color)
41     if color == "None":
42 jonathan 413 result = Color.None
43 bh 6 elif color[0] == '#':
44     if len(color) == 7:
45     r = string.atoi(color[1:3], 16) / 255.0
46     g = string.atoi(color[3:5], 16) / 255.0
47     b = string.atoi(color[5:7], 16) / 255.0
48     result = Color(r, g, b)
49     else:
50 jan 374 raise ValueError(_("Invalid hexadecimal color specification %s")
51 bh 6 % color)
52     else:
53 jan 374 raise ValueError(_("Invalid color specification %s") % color)
54 bh 6 return result
55    
56    
57 bh 267 class ProcessSession(xml.sax.handler.ContentHandler):
58 bh 6
59 bh 267 # Dictionary mapping element names (or (URI, element name) pairs for
60 jonathan 365 # documents using namespaces) to method names. The methods should
61 bh 267 # accept the same parameters as the startElement (or startElementNS)
62     # methods. The start_dispatcher is used by the default startElement
63     # and startElementNS methods to call a method for the open tag of an
64     # element.
65     start_dispatcher = {}
66    
67     # end_dispatcher works just like start_dispatcher but it's used by
68     # endElement and endElementNS. The method whose names it maps to
69     # should accept the same parameters as endElement and endElementNS.
70     end_dispatcher = {}
71    
72    
73 bh 6 def __init__(self, directory):
74     """Inititialize the Sax handler.
75    
76 bh 267 The directory parameter should be the directory containing the
77     session file. It's needed to interpret embedded relative
78     filenames.
79 bh 6 """
80     self.directory = directory
81     self.chars = ''
82     self.theSession = None
83     self.aMap = None
84     self.aLayer = None
85    
86 bh 267 def startElementNS(self, name, qname, attrs):
87     """Call the method given for name in self.start_dispatcher
88     """
89     if name[0] is None:
90     method_name = self.start_dispatcher.get(name[1])
91     else:
92     # Dispatch with namespace
93     method_name = self.start_dispatcher.get(name)
94     if method_name is not None:
95     getattr(self, method_name)(name, qname, attrs)
96 bh 6
97 bh 267 def endElementNS(self, name, qname):
98     """Call the method given for name in self.end_dispatcher
99     """
100     if name[0] is None:
101     method_name = self.end_dispatcher.get(name[1])
102     else:
103     # Dispatch with namespace
104     method_name = self.end_dispatcher.get(name)
105     if method_name is not None:
106     getattr(self, method_name)(name, qname)
107 bh 6
108 bh 267 def start_session(self, name, qname, attrs):
109     self.theSession = Session(attrs.get((None, 'title'), None))
110     start_dispatcher['session'] = "start_session"
111 bh 6
112 bh 267 def end_session(self, name, qname):
113     pass
114     end_dispatcher['session'] = "end_session"
115 bh 6
116 bh 267 def start_map(self, name, qname, attrs):
117     """Start a map."""
118     self.aMap = Map(attrs.get((None, 'title'), None))
119     start_dispatcher['map'] = "start_map"
120    
121     def end_map(self, name, qname):
122     self.theSession.AddMap(self.aMap)
123     end_dispatcher['map'] = "end_map"
124    
125     def start_projection(self, name, qname, attrs):
126     self.ProjectionParams = [ ]
127     start_dispatcher['projection'] = "start_projection"
128    
129     def end_projection(self, name, qname):
130     self.aMap.SetProjection(Projection(self.ProjectionParams))
131     end_dispatcher['projection'] = "end_projection"
132    
133     def start_parameter(self, name, qname, attrs):
134     s = attrs.get((None, 'value'))
135     s = str(s) # we can't handle unicode in proj
136     self.ProjectionParams.append(s)
137     start_dispatcher['parameter'] = "start_parameter"
138    
139     def start_layer(self, name, qname, attrs, layer_class = Layer):
140     """Start a layer
141    
142     Instantiate a layer of class layer_class from the attributes in
143     attrs which may be a dictionary as well as the normal SAX attrs
144     object and bind it to self.aLayer.
145     """
146     title = attrs.get((None, 'title'), "")
147     filename = attrs.get((None, 'filename'), "")
148     filename = os.path.join(self.directory, filename)
149     fill = parse_color(attrs.get((None, 'fill'), "None"))
150     stroke = parse_color(attrs.get((None, 'stroke'), "#000000"))
151     stroke_width = int(attrs.get((None, 'stroke_width'), "1"))
152     self.aLayer = layer_class(title, filename, fill = fill,
153     stroke = stroke, stroke_width = stroke_width)
154     start_dispatcher['layer'] = "start_layer"
155    
156     def end_layer(self, name, qname):
157     self.aMap.AddLayer(self.aLayer)
158     end_dispatcher['layer'] = "end_layer"
159    
160 jonathan 365 def start_classification(self, name, qname, attrs):
161 jonathan 413 self.aLayer.GetClassification().SetField(
162     attrs.get((None, 'field'), None))
163 jonathan 365 start_dispatcher['classification'] = "start_classification"
164    
165     def end_classification(self, name, qname):
166     pass
167     end_dispatcher['classification'] = "end_classification"
168    
169     def start_clnull(self, name, qname, attrs):
170 jonathan 413 self.cl_data = ClassDataDefault()
171     self.cl_data.SetLabel(attrs.get((None, 'label'), ""))
172 jonathan 365 start_dispatcher['clnull'] = "start_clnull"
173    
174     def end_clnull(self, name, qname):
175 jonathan 413 self.aLayer.GetClassification().SetDefaultData(self.cl_data)
176 jonathan 365 del self.cl_data
177     end_dispatcher['clnull'] = "end_clnull"
178    
179     def start_clpoint(self, name, qname, attrs):
180     attrib_value = attrs.get((None, 'value'), "0")
181    
182     try:
183 jonathan 413 value = Str2Num(attrib_value)
184 jonathan 365 except:
185 jonathan 413 value = attrib_value
186 jonathan 365
187 jonathan 413 self.cl_data = ClassDataPoint(value)
188     self.cl_data.SetLabel(attrs.get((None, 'label'), ""))
189    
190 jonathan 365 start_dispatcher['clpoint'] = "start_clpoint"
191    
192     def end_clpoint(self, name, qname):
193 jonathan 413 self.aLayer.GetClassification().AddClassData(self.cl_data)
194     del self.cl_data
195 jonathan 365 end_dispatcher['clpoint'] = "end_clpoint"
196    
197     def start_clrange(self, name, qname, attrs):
198    
199     try:
200 jonathan 413 min = Str2Num(attrs.get((None, 'min'), "0"))
201     max = Str2Num(attrs.get((None, 'max'), "0"))
202 jonathan 365 except ValueError:
203 jan 374 raise ValueError(_("Classification range is not a number!"))
204 jonathan 365
205 jonathan 413 self.cl_data = ClassDataRange(min, max)
206     self.cl_data.SetLabel(attrs.get((None, 'label'), ""))
207    
208 jonathan 365 start_dispatcher['clrange'] = "start_clrange"
209    
210     def end_clrange(self, name, qname):
211 jonathan 413 self.aLayer.GetClassification().AddClassData(self.cl_data)
212     del self.cl_data
213 jonathan 365 end_dispatcher['clrange'] = "end_clrange"
214    
215     def start_cldata(self, name, qname, attrs):
216 jonathan 390 self.cl_data.SetStroke(parse_color(attrs.get((None, 'stroke'), "None")))
217     self.cl_data.SetStrokeWidth(
218     int(attrs.get((None, 'stroke_width'), "0")))
219     self.cl_data.SetFill(parse_color(attrs.get((None, 'fill'), "None")))
220 jonathan 365 start_dispatcher['cldata'] = "start_cldata"
221    
222     def end_cldata(self, name, qname):
223     pass
224     end_dispatcher['cldata'] = "end_cldata"
225    
226 bh 267 def start_table(self, name, qname, attrs):
227     print "table title: %s" % attrs.get('title', None)
228     start_dispatcher['table'] = "start_table"
229    
230     def end_table(self, name, qname):
231     pass
232     end_dispatcher['table'] = "end_table"
233    
234     def start_labellayer(self, name, qname, attrs):
235     self.aLayer = self.aMap.LabelLayer()
236     start_dispatcher['labellayer'] = "start_labellayer"
237    
238     def start_label(self, name, qname, attrs):
239     x = float(attrs[(None, 'x')])
240     y = float(attrs[(None, 'y')])
241     text = attrs[(None, 'text')]
242     halign = attrs[(None, 'halign')]
243     valign = attrs[(None, 'valign')]
244     self.aLayer.AddLabel(x, y, text, halign = halign, valign = valign)
245     start_dispatcher['label'] = "start_label"
246    
247     def characters(self, chars):
248     pass
249    
250    
251 bh 6 def load_session(filename):
252     """Load a Thuban session from the file object file"""
253     dir = os.path.dirname(filename)
254     file = open(filename)
255     handler = ProcessSession(dir)
256    
257 bh 267 parser = make_parser()
258     parser.setContentHandler(handler)
259     parser.setErrorHandler(ErrorHandler())
260     parser.setFeature(xml.sax.handler.feature_namespaces, 1)
261     parser.parse(file)
262    
263 bh 6 session = handler.theSession
264     # Newly loaded session aren't modified
265     session.UnsetModified()
266    
267     return session
268    

Properties

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

[email protected]
ViewVC Help
Powered by ViewVC 1.1.26