1 """Class definition for the main QSkope window."""
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40 from PyQt4 import QtGui, QtCore
41
42 import pyffi.qskope.global_model
43 import pyffi.qskope.detail_model
44 import pyffi.qskope.detail_delegate
45
46 import pyffi
47 from pyffi.formats.nif import NifFormat
48 from pyffi.formats.cgf import CgfFormat
49 from pyffi.formats.kfm import KfmFormat
50 from pyffi.formats.dds import DdsFormat
51 from pyffi.formats.tga import TgaFormat
52 from pyffi.formats.egm import EgmFormat
53 from pyffi.formats.egt import EgtFormat
54 from pyffi.formats.esp import EspFormat
55 from pyffi.formats.tri import TriFormat
56 from pyffi.formats.bsa import BsaFormat
57 from pyffi.formats.rockstar.dir_ import DirFormat
58
59 from pyffi.object_models import FileFormat
60
61
62
63 -class QSkope(QtGui.QMainWindow):
64 """Main QSkope window."""
66 """Initialize the main window."""
67 QtGui.QMainWindow.__init__(self, parent)
68
69
70 self.createActions()
71 self.createMenus()
72
73
74 self.globalWidget = QtGui.QTreeView()
75 self.globalWidget.setAlternatingRowColors(True)
76
77
78 self.detailWidget = QtGui.QTreeView()
79 self.detailDelegate = pyffi.qskope.detail_delegate.DetailDelegate()
80 self.detailWidget.setItemDelegate(self.detailDelegate)
81 self.detailWidget.setAlternatingRowColors(True)
82
83
84
85
86 QtCore.QObject.connect(self.globalWidget,
87 QtCore.SIGNAL("clicked(const QModelIndex &)"),
88 self.setDetailModel)
89
90
91 self.splitter = QtGui.QSplitter()
92 self.splitter.addWidget(self.globalWidget)
93 self.splitter.addWidget(self.detailWidget)
94 self.setCentralWidget(self.splitter)
95
96
97 self.statusBar().clearMessage()
98
99
100 self.setWindowTitle("QSkope")
101
102
103 self.data = None
104
105
106 settings = self.getSettings(versioned = True)
107 self.restoreGeometry(
108 settings.value("MainWindow/geometry").toByteArray())
109
111 """Create the menu actions."""
112
113 self.openAct = QtGui.QAction("&Open", self)
114 self.openAct.setShortcut("Ctrl+O")
115 QtCore.QObject.connect(self.openAct,
116 QtCore.SIGNAL("triggered()"),
117 self.openAction)
118
119
120 self.saveAct = QtGui.QAction("&Save", self)
121 self.saveAct.setShortcut("Ctrl+S")
122 QtCore.QObject.connect(self.saveAct,
123 QtCore.SIGNAL("triggered()"),
124 self.saveAction)
125
126
127 self.saveAsAct = QtGui.QAction("Save As...", self)
128 self.saveAsAct.setShortcut("Ctrl+Shift+S")
129 QtCore.QObject.connect(self.saveAsAct,
130 QtCore.SIGNAL("triggered()"),
131 self.saveAsAction)
132
133
134 self.exitAct = QtGui.QAction("E&xit", self)
135 self.exitAct.setShortcut("Ctrl+Q")
136 QtCore.QObject.connect(self.exitAct,
137 QtCore.SIGNAL("triggered()"),
138 QtGui.qApp.quit)
139
140
141 self.aboutQSkopeAct = QtGui.QAction("About QSkope", self)
142 QtCore.QObject.connect(self.aboutQSkopeAct,
143 QtCore.SIGNAL("triggered()"),
144 self.aboutQSkopeAction)
145
146
147 self.aboutQtAct = QtGui.QAction("About Qt", self)
148 QtCore.QObject.connect(self.aboutQtAct,
149 QtCore.SIGNAL("triggered()"),
150 QtGui.qApp.aboutQt)
151
152
153
155 """Create the menu bar."""
156
157 fileMenu = self.menuBar().addMenu("&File")
158 fileMenu.addAction(self.openAct)
159 fileMenu.addAction(self.saveAct)
160 fileMenu.addAction(self.saveAsAct)
161 fileMenu.addSeparator()
162 fileMenu.addAction(self.exitAct)
163
164
165 helpMenu = self.menuBar().addMenu("&Help")
166 helpMenu.addAction(self.aboutQSkopeAct)
167 helpMenu.addAction(self.aboutQtAct)
168
170 """Called when the application is closed. Saves the settings."""
171 settings = self.getSettings(versioned = True)
172 settings.setValue("MainWindow/geometry",
173 QtCore.QVariant(self.saveGeometry()))
174 QtGui.QMainWindow.closeEvent(self, event)
175
176
177
178
179
180
182 """Open a file, and set up the view."""
183
184 self.statusBar().showMessage("Reading %s ..." % filename)
185
186
187
188 try:
189 stream = open(filename, "rb")
190
191 for Format in (NifFormat, CgfFormat, KfmFormat, DdsFormat,
192 TgaFormat, EgmFormat, EspFormat, TriFormat,
193 EgtFormat, BsaFormat, DirFormat):
194 self.data = Format.Data()
195 try:
196 self.data.read(stream)
197 except ValueError as err:
198
199 print(str(err))
200 continue
201 else:
202 break
203 else:
204
205
206 self.statusBar().showMessage(
207 'File format of %s not recognized'
208 % filename)
209 return
210
211 except (ValueError, IOError):
212
213 self.statusBar().showMessage("Failed reading %s (see console)"
214 % filename)
215 raise
216
217 else:
218
219 self.fileName = filename
220
221
222 self.statusBar().showMessage("Finished reading %s" % filename)
223
224
225 self.globalModel = pyffi.qskope.global_model.GlobalModel(
226 globalnode=self.data)
227 self.globalWidget.setModel(self.globalModel)
228 self.setDetailModel(
229 self.globalModel.index(0, 0, QtCore.QModelIndex()))
230
231
232 self.setWindowTitle("QSkope - %s" % self.fileName)
233 finally:
234 try:
235 stream.close()
236 except UnboundLocalError:
237 pass
238
240 """Save changes to disk."""
241
242
243 if self.data is None:
244 self.statusBar().showMessage("Saving this format not supported")
245 return
246
247
248 self.statusBar().showMessage("Saving %s ..." % filename)
249 try:
250
251 stream = open(filename, "wb")
252
253 self.data.write(stream)
254
255 except ValueError:
256
257 self.statusBar().showMessage("Failed saving %s (see console)"
258 % filename)
259 raise
260 else:
261
262 self.statusBar().showMessage("Finished saving %s" % filename)
263 finally:
264 stream.close()
265
266 @staticmethod
268 """Return the QSkope settings."""
269 if not versioned:
270 return QtCore.QSettings("PyFFI", "QSkope")
271 else:
272 return QtCore.QSettings("PyFFI-%s" % pyffi.__version__, "QSkope")
273
274
275
276
277
291
293 """Open a file."""
294
295
296 filename = QtGui.QFileDialog.getOpenFileName(self, "Open File")
297 if filename:
298 self.openFile(filename = filename)
299
301 """Save a file."""
302
303
304 filename = QtGui.QFileDialog.getSaveFileName(self, "Save File")
305 if filename:
306 self.fileName = filename
307 self.saveAction()
308
310 """Save a file."""
311
312
313 if self.fileName:
314 self.saveFile(filename = self.fileName)
315
317 """Display an information window about QSkope."""
318
319 mbox = QtGui.QMessageBox(self)
320
321 mbox.setWindowTitle("About QSkope")
322 mbox.setText("""
323 <p>QSkope is a tool bundled with PyFFI for analyzing and editing files whose
324 format is supported by pyffi. QSkope is written in Python.</p>
325 <p>The Python File Format Interface, or briefly PyFFI, is a general purpose
326 library to read and write block structured file formats.</p>
327 <p>For more informations visit
328 <a href="http://pyffi.sourceforge.net">http://pyffi.sourceforge.net</a>.</p>
329 <p>PyFFI is free software and comes under a BSD license. The source is
330 available via
331 <a href="http://pyffi.svn.sourceforge.net/viewvc/pyffi/trunk/">svn</a>
332 on <a href="http://sourceforge.net">SourceForge</a>.</p>
333 <p>You are running PyFFI %s.
334 The most recent version of PyFFI can always be downloaded from the
335 <a href="http://sourceforge.net/projects/pyffi/files/">
336 PyFFI SourceForge Project page</a>.""" % pyffi.__version__)
337
338 mbox.exec_()
339