From 17e5164ab467435ae8c8aa8a58c8167693891060 Mon Sep 17 00:00:00 2001 From: Allanis <allanis@saracraft.net> Date: Sat, 13 Apr 2013 15:01:41 +0100 Subject: [PATCH] [Add] Initial code for resource editor. --- utils/resedit/data.py | 41 +++++ utils/resedit/data.pyc | Bin 0 -> 1507 bytes utils/resedit/resedit.py | 11 ++ utils/resedit/space.glade | 360 ++++++++++++++++++++++++++++++++++++++ utils/resedit/space.py | 132 ++++++++++++++ utils/resedit/space.pyc | Bin 0 -> 4733 bytes 6 files changed, 544 insertions(+) create mode 100644 utils/resedit/data.py create mode 100644 utils/resedit/data.pyc create mode 100755 utils/resedit/resedit.py create mode 100644 utils/resedit/space.glade create mode 100644 utils/resedit/space.py create mode 100644 utils/resedit/space.pyc diff --git a/utils/resedit/data.py b/utils/resedit/data.py new file mode 100644 index 0000000..85b9dfb --- /dev/null +++ b/utils/resedit/data.py @@ -0,0 +1,41 @@ +#!/usr/bin/env python + +from xml.dom import minidom + +def load(xmlfile, tag, has_name=True, do_array=None): + dom = minidom.parse(xmlfile) + xmlNodes = dom.getElementsByTagName(tag) + + dictionary = {} + for xmlNode in xmlNodes: + mdic = {} + # Name is stored as a property and not a node. + if(has_name): + name = xmlNode.attributes["name"].value + + # Process the nodes. + for bignode in filter(lambda x: x.nodeType==x.ELEMENT_NODE, xmlNode.childNodes): + # Load the nodes. + section = {} + array = [] + for node in filter(lambda x: x.nodeType==x.ELEMENT_NODE, + bignode.childNodes): + if bignode.nodeName in do_array: # Big ugly hack to use list instead of array. + array.append(node.firstChild.data) + else: # Normal way (but will overwrite lists). + section[node.nodeName] = node.firstChild.data + + if len(array) > 0: + mdic[bignode.nodeName] = array + else: + mdic[bignode.nodeName] = section + + # Append the element to the dictionary. + dictionary[name] = mdic + + dom.unlink() + return dictionary + +def save(xmlfile, basetag, tag, has_name=True): + print "TODO" + diff --git a/utils/resedit/data.pyc b/utils/resedit/data.pyc new file mode 100644 index 0000000000000000000000000000000000000000..0d44609e3418730d99b828323678b91de6a38745 GIT binary patch literal 1507 zcmb_c&2AGx4EAi&gr-Sb{)L28sTU%U8Xlmk5Hx}Vq_6~4ssz<EJ56W1KVfHr5@~aS zGk4yCE3d<m0|$5j`0On|S5%^oYmYzM-*`M*``&4NePy4G=<HX+|9e=j2NB^<Q9_g| zI#8rcKvA8dfZhdkP$xEP^bWoy-hbX*LX7=^Uspl%O^DQHHp<gc9r`L(1M2~n+W^E9 z#fnOzw~7{ZD(e&nR4Or-$Pz6YH2Xs3679bHOpB&$U7#|c;whC)ifhd8MqH=GGG#=w zkK{oG{7BpldK)1011(w-x<X^*Y}4$8;J_WY7R6_{9a?n6Zc<sJ(*_lvsBBY=iXDoV zDQ+<{_4@rEyIc{yN!!@n_psWGK{rn8RD5HzL^x_N<d_)$x4q9+gUV%i@6bMX011c` zHmiOPJhv{>sTpxoc?DR{vD`WYx))bc(P@AnMhv=)@fRSnJTk-i#P~Lh{^S0W{$O}G z*xT(_cf{yf7lK5%yU=<kd1`t(Npxmi&lRKIV>3Ci&gZ?Uw~6Z&#+k_aUZlO=n#`rn zcB0dxNbg)k0>}COnQq9OLmoh(7V^2z$t>iFyox1^Fi^<Yfe2Z{s1Qwb;f%imZESo$ zF{#PCyFVZ5@c=FNEjYCIg*}>j<0RsZPNv5593R`nn?f+76PrW>wA%e{y2LX~PbMad z1a@o-=N~XuZk7Az`M?RPGIW|HHaqR|Ly^}rOA{0^g7JDRxlgn^<Z%!q$`5r>=(!;9 z&SVo&6%}S5*^#$-ri=NnjO>&0DSROhfOwAVm}f<FXCz3@TjiG_g!`NqB6X8oN8EdN z8-moDS_>MgqZ*KxYd0Yqs;$<se=WEkTvF@7#oB7nQt}O99!y!jA<Izk0eJW*!h?{J zuU^Y=Z+EXE%JA?KM0G@syVm3IGVk)8|Bur+{l?rvF300bYS872{MG9%+(|WT%w$+# ka#$JUnF%+bgqsk5ScrCxH<;$pG%-6oQjY7a2Wy)@0d=i6fB*mh literal 0 HcmV?d00001 diff --git a/utils/resedit/resedit.py b/utils/resedit/resedit.py new file mode 100755 index 0000000..4150247 --- /dev/null +++ b/utils/resedit/resedit.py @@ -0,0 +1,11 @@ +#!/usr/bin/env python + +import space + +# Load the universe. +universe = space.space() +universe.loadSystems("../../dat/ssys.xml") +universe.loadPlanets("../../dat/planet.xml") +universe.debug() +universe.window() + diff --git a/utils/resedit/space.glade b/utils/resedit/space.glade new file mode 100644 index 0000000..41055f2 --- /dev/null +++ b/utils/resedit/space.glade @@ -0,0 +1,360 @@ +<?xml version="1.0" encoding="UTF-8" standalone="no"?> +<!DOCTYPE glade-interface SYSTEM "glade-2.0.dtd"> +<!--Generated with glade3 3.4.1 on Thu Feb 7 11:50:56 2008 --> +<glade-interface> + <widget class="GtkWindow" id="winSystems"> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="title" translatable="yes">Systems</property> + <property name="default_width">600</property> + <property name="default_height">420</property> + <property name="type_hint">GDK_WINDOW_TYPE_HINT_DIALOG</property> + <child> + <widget class="GtkVBox" id="vbox1"> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <child> + <widget class="GtkHPaned" id="hpaned1"> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <child> + <widget class="GtkTreeView" id="treSystems"> + <property name="width_request">100</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="headers_clickable">True</property> + </widget> + <packing> + <property name="resize">False</property> + <property name="shrink">True</property> + </packing> + </child> + <child> + <widget class="GtkLayout" id="layout1"> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <child> + <widget class="GtkLabel" id="label1"> + <property name="width_request">67</property> + <property name="height_request">31</property> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="label" translatable="yes">Name:</property> + </widget> + <packing> + <property name="x">31</property> + <property name="y">26</property> + </packing> + </child> + <child> + <widget class="GtkEntry" id="inpName"> + <property name="width_request">134</property> + <property name="height_request">20</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="truncate_multiline">True</property> + </widget> + <packing> + <property name="x">95</property> + <property name="y">31</property> + </packing> + </child> + <child> + <widget class="GtkLabel" id="labPos"> + <property name="width_request">65</property> + <property name="height_request">25</property> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="label" translatable="yes">X,Y</property> + </widget> + <packing> + <property name="x">242</property> + <property name="y">28</property> + </packing> + </child> + <child> + <widget class="GtkButton" id="butRepos"> + <property name="width_request">75</property> + <property name="height_request">33</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="receives_default">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="label" translatable="yes">Reposition</property> + <property name="response_id">0</property> + </widget> + <packing> + <property name="x">319</property> + <property name="y">23</property> + </packing> + </child> + <child> + <widget class="GtkLabel" id="label2"> + <property name="width_request">103</property> + <property name="height_request">28</property> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="label" translatable="yes">Interference</property> + </widget> + <packing> + <property name="x">19</property> + <property name="y">75</property> + </packing> + </child> + <child> + <widget class="GtkHSeparator" id="hseparator1"> + <property name="width_request">402</property> + <property name="height_request">20</property> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + </widget> + <packing> + <property name="x">6</property> + <property name="y">55</property> + </packing> + </child> + <child> + <widget class="GtkSpinButton" id="spiInterference"> + <property name="width_request">74</property> + <property name="height_request">20</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="adjustment">0 0 100 1 10 10</property> + </widget> + <packing> + <property name="x">117</property> + <property name="y">79</property> + </packing> + </child> + <child> + <widget class="GtkLabel" id="label3"> + <property name="width_request">75</property> + <property name="height_request">20</property> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="label" translatable="yes">Asteroids</property> + </widget> + <packing> + <property name="x">29</property> + <property name="y">114</property> + </packing> + </child> + <child> + <widget class="GtkSpinButton" id="spiAsteroids"> + <property name="width_request">72</property> + <property name="height_request">20</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="adjustment">0 0 100 1 10 10</property> + </widget> + <packing> + <property name="x">119</property> + <property name="y">113</property> + </packing> + </child> + <child> + <widget class="GtkLabel" id="label4"> + <property name="width_request">68</property> + <property name="height_request">20</property> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="label" translatable="yes">Stars</property> + </widget> + <packing> + <property name="x">32</property> + <property name="y">144</property> + </packing> + </child> + <child> + <widget class="GtkSpinButton" id="spiStars"> + <property name="width_request">73</property> + <property name="height_request">20</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="adjustment">0 0 100 1 10 10</property> + </widget> + <packing> + <property name="x">120</property> + <property name="y">143</property> + </packing> + </child> + <child> + <widget class="GtkVSeparator" id="vseparator1"> + <property name="width_request">20</property> + <property name="height_request">259</property> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + </widget> + <packing> + <property name="x">202</property> + <property name="y">72</property> + </packing> + </child> + <child> + <widget class="GtkDrawingArea" id="draSpace"> + <property name="width_request">180</property> + <property name="height_request">171</property> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + </widget> + <packing> + <property name="x">221</property> + <property name="y">88</property> + </packing> + </child> + <child> + <widget class="GtkHSeparator" id="hseparator2"> + <property name="width_request">204</property> + <property name="height_request">20</property> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + </widget> + <packing> + <property name="x">5</property> + <property name="y">169</property> + </packing> + </child> + <child> + <widget class="GtkTreeView" id="treJumps"> + <property name="width_request">193</property> + <property name="height_request">86</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="headers_clickable">True</property> + </widget> + <packing> + <property name="x">10</property> + <property name="y">205</property> + </packing> + </child> + <child> + <widget class="GtkButton" id="butAddJump"> + <property name="width_request">70</property> + <property name="height_request">27</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="receives_default">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="label" translatable="yes">Add</property> + <property name="response_id">0</property> + </widget> + <packing> + <property name="x">25</property> + <property name="y">298</property> + </packing> + </child> + <child> + <widget class="GtkButton" id="butRmJump"> + <property name="width_request">70</property> + <property name="height_request">29</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="receives_default">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="label" translatable="yes">Delete</property> + <property name="response_id">0</property> + </widget> + <packing> + <property name="x">121</property> + <property name="y">298</property> + </packing> + </child> + <child> + <widget class="GtkLabel" id="label5"> + <property name="width_request">126</property> + <property name="height_request">20</property> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="label" translatable="yes">Jumps</property> + </widget> + <packing> + <property name="x">44</property> + <property name="y">184</property> + </packing> + </child> + <child> + <widget class="GtkLabel" id="labSpace"> + <property name="width_request">100</property> + <property name="height_request">20</property> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="label" translatable="yes">Space</property> + </widget> + <packing> + <property name="x">263</property> + <property name="y">69</property> + </packing> + </child> + <child> + <widget class="GtkHSeparator" id="hseparator3"> + <property name="width_request">190</property> + <property name="height_request">20</property> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + </widget> + <packing> + <property name="x">218</property> + <property name="y">265</property> + </packing> + </child> + <child> + <widget class="GtkButton" id="butSave"> + <property name="width_request">87</property> + <property name="height_request">38</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="receives_default">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="label" translatable="yes">Save</property> + <property name="response_id">0</property> + </widget> + <packing> + <property name="x">227</property> + <property name="y">290</property> + </packing> + </child> + <child> + <widget class="GtkButton" id="butDone"> + <property name="width_request">83</property> + <property name="height_request">41</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="receives_default">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="label" translatable="yes">Done</property> + <property name="response_id">0</property> + </widget> + <packing> + <property name="x">322</property> + <property name="y">288</property> + </packing> + </child> + </widget> + <packing> + <property name="resize">True</property> + <property name="shrink">False</property> + </packing> + </child> + </widget> + </child> + <child> + <widget class="GtkStatusbar" id="staBottom"> + <property name="visible">True</property> + <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> + <property name="spacing">2</property> + </widget> + <packing> + <property name="expand">False</property> + <property name="position">1</property> + </packing> + </child> + </widget> + </child> + </widget> +</glade-interface> diff --git a/utils/resedit/space.py b/utils/resedit/space.py new file mode 100644 index 0000000..8e9d72d --- /dev/null +++ b/utils/resedit/space.py @@ -0,0 +1,132 @@ +#!/usr/bin/env python + +try: + import gtk,gtk.glade + import gobject +except: + print "You do not have python gtk bindings, or you're missing glade libs" + print "To use Lephisto's resedit you must install them" + print "http://pygtk.org/ " + raise SystemExit + +import data + +class space: + + def __init__(self): + self.glade = "space.glade" + self.systemsXML = "../../dat/ssys.xml" + self.planetsXML = "../../dat/planet.xml" + self.loadSystems(self.systemsXML) + self.loadPlanets(self.planetsXML) + + def loadSystems(self, xmlfile): + self.systems = data.load(xmlfile, "ssys", True, ["jumps","fleets","planets"]) + + + def saveSystems(self, xmlfile): + print "TODO" + + + def loadPlanets(self, xmlfile): + self.planets = data.load(xmlfile, "planet", True, ["commodities"]) + + + def savePlanets(self, xmlfile): + print "TODO" + + + def window(self): + """ + create the window + """ + # --------------- SYSTEMS -------------------- + self.swtree = gtk.glade.XML(self.glade, "winSystems") + + # Hook events and stuff. + self.__swidget("winSystems").connect("destroy", self.__done) + self.__swidget("butDone").connect("clicked", self.__done) + self.__swidget("treSystems").connect("row-activated", self.__update) + + # Populate the tree. + self.tree_systems = gtk.TreeStore(str) + for system in self.systems: # Load the planets. + treenode = self.tree_systems.append(None, [system]) + for planet in self.systems[system]['planets']: + self.tree_systems.append(treenode, [planet]) + col = gtk.TreeViewColumn('Systems') + cell = gtk.CellRendererText() + self.__swidget("treSystems").append_column(col) + col.pack_start(cell, True) + col.add_attribute(cell, 'text', 0) + self.__swidget("treSystems").set_model(self.tree_systems) + + # Display the window and such. + self.__swidget("winSystems").show_all() + + # ---------------- PLANETS -------------------- + + # --------------------------------------------- + gtk.main() + + + def __swidget(self,wgtname): + """ + get a widget from the winSystems + """ + return self.swtree.get_widget(wgtname) + + + def __update(self, wgt=None, foo=None, bar=None): + """ + Update the window + """ + # Important thingies. + tree = self.__swidget("treSystems") + model = tree.get_model() + + # Get system. + sel = model.iter_nth_child(None, foo[0]) + sys_name = model.get_value( sel, 0 ) + system = self.systems[sys_name] + + # Load it all. + dic = { + "inpName":sys_name, + "spiInterference":system["general"]["interference"], + "spiAsteroids":system["general"]["asteroids"], + "spiStars":system["general"]["stars"], + "labPos":"%s,%s" % (system["pos"]["x"],system["pos"]["y"]) + } + for key, value in dic.items(): + self.__swidget(key).set_text(value) + + # Load jumps. + + jumps = gtk.ListStore(str) + for jump in system["jumps"]: # Load the planets. + treenode = jumps.append([jump]) + col = gtk.TreeViewColumn('Jumps') + cell = gtk.CellRendererText() + wgt = self.__swidget("treJumps") + if wgt.get_column(0): + wgt.remove_column( wgt.get_column(0) ) + wgt.append_column(col) + col.pack_start(cell, True) + col.add_attribute(cell, 'text', 0) + wgt.set_model(jumps) + + def __done(self, widget=None, data=None): + """ + Window is done + """ + gtk.main_quit() + + def debug(self): + print "SYSTEMS LOADED:" + print self.systems + print + print + print "PLANETS LOADED:" + print self.planets + diff --git a/utils/resedit/space.pyc b/utils/resedit/space.pyc new file mode 100644 index 0000000000000000000000000000000000000000..1acd9b0b478a0c5278df476f948921ddecf93871 GIT binary patch literal 4733 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 am51!toOt~MA;f`WJqQ6azst3i+J6D6Y}Gvg literal 0 HcmV?d00001