/[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 374 - (hide annotations)
Mon Jan 27 14:20:02 2003 UTC (22 years, 1 month ago) by jan
Original Path: trunk/thuban/Thuban/Model/load.py
File MIME type: text/x-python
File size: 8963 byte(s)
Replace user string by _() for i18n.

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

Properties

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

[email protected]
ViewVC Help
Powered by ViewVC 1.1.26