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

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

Parent Directory Parent Directory | Revision Log Revision Log


Revision 723 - (show annotations)
Thu Apr 24 15:31:53 2003 UTC (21 years, 10 months ago) by bh
Original Path: trunk/thuban/Thuban/Model/session.py
File MIME type: text/x-python
File size: 5911 byte(s)
First step towards table management. Introduce a simple data
abstraction so that we replace the data a layer uses more easily
in the next step.

* Thuban/Model/data.py: New file with a simple data abstraction
that bundles shapefile and dbffile into one object.

* Thuban/Model/session.py (Session.OpenShapefile): New method to
open shapefiles and return a shape store object

* Thuban/Model/layer.py (Layer.__init__): Pass the data as a store
object instead of a shapefile filename. This introduces a new
instance variable store holding the datastore. For intermediate
backwards compatibility keep the old instance variables.
(open_shapefile): Removed. No longer needed with the shape store.
(Layer.SetShapeStore, Layer.ShapeStore): New methods to set and
get the shape store used by a layer.
(Layer.Destroy): No need to explicitly destroy the shapefile or
table anymore.

* Thuban/UI/mainwindow.py (MainWindow.AddLayer)
(MainWindow.AddLayer): Use the session's OpenShapefile method to
open shapefiles

* Thuban/Model/load.py (ProcessSession.start_layer): Use the
session's OpenShapefile method to open shapefiles

* test/test_classification.py
(TestClassification.test_classification): Use the session's
OpenShapefile method to open shapefiles and build the filename in
a more platform independed way

* test/test_layer.py (TestLayer.setUp, TestLayer.tearDown):
Implement to have a session to use in the tests
(TestLayer.test_arc_layer, TestLayer.test_polygon_layer)
(TestLayer.test_point_layer, TestLayer.test_empty_layer): Use the
session's OpenShapefile method to open shapefiles
(TestLayerLegend.setUp): Instantiate a session so that we can use
it to open shapefiles.
(TestLayerLegend.tearDown): Make sure that all references to
layers and session are removed otherwise we may get a resource
leak

* test/test_map.py (TestMapAddLayer.test_add_layer)
(TestMapWithContents.setUp): Instantiate a session so that we can
use it to open shapefiles.
(TestMapWithContents.tearDown): Make sure that all references to
layers, maps and sessions are removed otherwise we may get a
resource leak
("__main__"): use support.run_tests() so that more info about
uncollected garbage is printed

* test/test_save.py (SaveSessionTest.testSingleLayer): Use the
session's OpenShapefile method to open shapefiles
("__main__"): use support.run_tests() so that more info about
uncollected garbage is printed

* test/test_selection.py (TestSelection.tearDown): Make sure that
all references to the session and the selection are removed
otherwise we may get a resource leak
(TestSelection.get_layer): Instantiate a session so that we can
use it to open shapefiles.
("__main__"): use support.run_tests() so that more info about
uncollected garbage is printed

* test/test_session.py (TestSessionBase.tearDown)
(TestSessionWithContent.tearDown): Make sure that all references
to the session and layers are removed otherwise we may get a
resource leak
(TestSessionWithContent.setUp): Use the session's OpenShapefile
method to open shapefiles

1 # Copyright (c) 2001, 2002, 2003 by Intevation GmbH
2 # Authors:
3 # Bernhard Herzog <[email protected]>
4 # Jan-Oliver Wagner <[email protected]>
5 #
6 # This program is free software under the GPL (>=v2)
7 # Read the file COPYING coming with Thuban for details.
8
9 __version__ = "$Revision$"
10
11 from messages import MAPS_CHANGED, EXTENSIONS_CHANGED, FILENAME_CHANGED, \
12 MAP_LAYERS_CHANGED, MAP_PROJECTION_CHANGED, \
13 LAYER_CHANGED, LAYER_PROJECTION_CHANGED, LAYER_VISIBILITY_CHANGED,\
14 EXTENSION_CHANGED, EXTENSION_OBJECTS_CHANGED, CHANGED
15
16 from Thuban import _
17
18 from base import TitledObject, Modifiable
19 from map import Map
20 from data import ShapefileStore
21
22
23 class Session(TitledObject, Modifiable):
24
25 """A complete session.
26
27 A Session consists of arbitrary numbers of maps, tables and extensions
28
29 Session objects send the following events:
30
31 TITLE_CHANGED -- The title has changed. Parameters: the session.
32
33 FILENAME_CHANGED -- The filename has changed. No parameters.
34
35 MAPS_CHANGED -- Maps were added, removed.
36
37 EXTENSIONS_CHANGED -- Extensions were added, removed.
38
39 MAP_LAYERS_CHANGED -- Same as the map's event of the same name.
40 It's simply resent from the session to make
41 subscriptions easier.
42
43 CHANGED -- Generic changed event. Parameters: the session. The
44 event is always issued when any other changed event
45 is issused. This is useful for code that needs to be
46 notified whenever something in the session has
47 changed but it's too cumbersome or error-prone to
48 subscribe to all the individual events.
49 """
50
51 # message channels that have to be forwarded from maps contained in
52 # the session.
53 forwarded_channels = (
54 # generic channels
55 CHANGED,
56
57 # map specific channels
58 MAP_PROJECTION_CHANGED,
59 MAP_LAYERS_CHANGED,
60
61 # layer channels forwarded by the map
62 LAYER_PROJECTION_CHANGED,
63 LAYER_CHANGED,
64 LAYER_VISIBILITY_CHANGED,
65
66 # channels forwarded by an extension
67 EXTENSION_CHANGED,
68 EXTENSION_OBJECTS_CHANGED)
69
70 def __init__(self, title):
71 TitledObject.__init__(self, title)
72 Modifiable.__init__(self)
73 self.filename = None
74 self.maps = []
75 self.tables = []
76 self.extensions = []
77
78 def changed(self, channel = None, *args):
79 """Like the inherited version but issue a CHANGED message as well.
80
81 The CHANGED message is only issued if channel given is a
82 different channel than CHANGED.
83 """
84 Modifiable.changed(self, channel, *args)
85 if channel != CHANGED:
86 self.issue(CHANGED, self)
87
88 def SetFilename(self, filename):
89 self.filename = filename
90 self.changed(FILENAME_CHANGED)
91
92 def Maps(self):
93 return self.maps
94
95 def HasMaps(self):
96 return len(self.maps) > 0
97
98 def AddMap(self, map):
99 self.maps.append(map)
100 for channel in self.forwarded_channels:
101 map.Subscribe(channel, self.forward, channel)
102 self.changed(MAPS_CHANGED)
103
104 def RemoveMap(self, map):
105 for channel in self.forwarded_channels:
106 map.Unsubscribe(channel, self.forward, channel)
107 self.maps.remove(map)
108 self.changed(MAPS_CHANGED)
109 map.Destroy()
110
111 def Extensions(self):
112 return self.extensions
113
114 def HasExtensions(self):
115 return len(self.extensions) > 0
116
117 def AddExtension(self, extension):
118 self.extensions.append(extension)
119 for channel in self.forwarded_channels:
120 extension.Subscribe(channel, self.forward, channel)
121 self.changed(EXTENSIONS_CHANGED)
122
123 def OpenShapefile(self, filename):
124 """Return a shapefile store object for the data in the given file"""
125 return ShapefileStore(self, filename)
126
127 def Destroy(self):
128 for map in self.maps:
129 map.Destroy()
130 self.maps = []
131 self.tables = []
132 Modifiable.Destroy(self)
133
134 def forward(self, *args):
135 """Reissue events.
136
137 If the channel the event is forwarded to is a changed-channel
138 that is not the CHANGED channel issue CHANGED as well. An
139 channel is considered to be a changed-channel if it's name ends
140 with 'CHANGED'.
141 """
142 if len(args) > 1:
143 args = (args[-1],) + args[:-1]
144 apply(self.issue, args)
145 channel = args[0]
146 # It's a bit of a kludge to rely on the channel name for this.
147 if channel.endswith("CHANGED") and channel != CHANGED:
148 self.issue(CHANGED, self)
149
150 def WasModified(self):
151 """Return true if the session or one of the maps was modified"""
152 if self.modified:
153 return 1
154 else:
155 for map in self.maps:
156 if map.WasModified():
157 return 1
158 return 0
159
160 def UnsetModified(self):
161 """Unset the modified flag of the session and the maps"""
162 Modifiable.UnsetModified(self)
163 for map in self.maps:
164 map.UnsetModified()
165
166 def TreeInfo(self):
167 items = []
168 if self.filename is None:
169 items.append(_("Filename:"))
170 else:
171 items.append(_("Filename: %s") % self.filename)
172
173 if self.WasModified():
174 items.append(_("Modified"))
175 else:
176 items.append(_("Unmodified"))
177
178 items.extend(self.maps)
179 items.extend(self.extensions)
180
181 return (_("Session: %s") % self.title, items)
182
183
184 def create_empty_session():
185 """Return an empty session useful as a starting point"""
186 import os
187 session = Session(_('unnamed session'))
188 session.SetFilename(None)
189 session.AddMap(Map(_('unnamed map')))
190 session.UnsetModified()
191 return session

Properties

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

[email protected]
ViewVC Help
Powered by ViewVC 1.1.26