def addStoryRowNew(caller,parent,ed,target): row = gtk.HBox() row.show() text = "Please enter the short code for this story" label = "Code:" subtext = "\ This will be what is displayed in your\n\ backend files. Once set, it cannot be\n\ changed within this program. It may\n\ contain word characters (A-Z,0-9,_,-)\n\ only." code = common.askBox(ed,text,label,subtext=subtext,nospace=True) code = common.validateFileid(code) if code and len(code) > 0: label = gtk.Label(code) label.show() label.set_width_chars(4) row.pack_start(label,False,False,2) entry = gtk.Entry() entry.show() entry.set_width_chars(20) row.pack_start(entry,False,False,2) target.pack_start(row,False,False,2) entry.grab_focus() entry.connect("focus-out-event",setStory,code) refreshEd(parent,ed) else: status.push(0,"Story add cancelled.") return False
def storyPicker(parent,name,value): global picklist global stories picklist = common.csplit(str(value)) title = "Stories involving %s" % name if not len(stories): stories = myStories(config.get("realmdir")) askbox = gtk.Dialog(title,parent,gtk.DIALOG_DESTROY_WITH_PARENT,None) askbox.add_button("Cancel",1) askbox.add_button("Set",0) for key in sorted(stories.keys()): title = stories.get(key,"") if title and len(title) > 0: button = gtk.CheckButton(title) button.show() button.unset_flags(gtk.CAN_FOCUS) button.connect("toggled",updatePicklist,key) if not picklist: picklist = [] if key in picklist: button.set_active(True) askbox.vbox.pack_start(button,True,True,2) # OK button closes dialog, turns keys into a csv string and returns it (nondefined values, plus defined that are checked) askbox.move(config['pos'][0] + 50,config['pos'][1] + 50) value = askbox.run() askbox.destroy() if value == 0: output = "" for k in range(len(picklist)): if k > 0: output += ", " output += picklist[k] return output else: status.push(0,"Cancel: Stories not modified.") return None
def connectToPlace(parent,target,tabs,scroll,fileid,ar,plalts,title = ""): global status relid = recordSelectBox(None,fileid,title,['l','p']) # TODO: organizations? if relid and len(relid[1]): addRelToBox(parent,target,relid,fileid,tabs,scroll,ar,plalts) status.push(0,"Added connection to %s on %s" % (relid[0],fileid)) else: status.push(0,"Adding connection on %s cancelled" % fileid)
def connectToPerson(parent,target,tabs,scroll,fileid,title = ""): global status relid = recordSelectBox(None,fileid,title) if relid and len(relid[1]): addRelToBox(parent,target,relid,fileid,tabs,scroll) status.push(0,"Added connection to %s on %s" % (relid,fileid)) else: status.push(0,"Adding connection on %s cancelled" % fileid)
def saveThisP(caller,fileid): global status if people.get(fileid): if savePerson(fileid,people[fileid]): status.push(0,"%s saved successfully." % fileid) else: status.push(0,"Error encountered saving %s." % fileid) else: bsay(caller,"saveThisP: Could not find person %s." % fileid)
def saveThisC(caller, fileid): global status if cities.get(fileid): if saveCity(fileid, cities[fileid]): status.push(0, "%s saved successfully." % fileid) else: status.push(0, "Error encountered saving %s." % fileid) else: bsay(caller, "saveThisC: Could not find city %s." % fileid)
def saveThisL(caller,fileid): global status if places.get(fileid): if savePlace(fileid,places[fileid]): status.push(0,"%s saved successfully." % fileid) else: status.push(0,"Error encountered saving %s." % fileid) else: bsay(caller,"saveThisL: Could not find place %s." % fileid)
def saveThisS(caller,fileid): global status if states.get(fileid): pushLoc(fileid,states[fileid].get('name')) if saveState(fileid,states[fileid]): status.push(0,"%s saved successfully." % fileid) else: status.push(0,"Error encountered saving %s." % fileid) else: bsay(caller,"saveThisS: Could not find state %s." % fileid)
def writefile(fn,lines,create = False): if create or os.path.exists(os.path.abspath(fn)): try: f = codecs.open(os.path.abspath(fn),'wU',"UTF-8") f.writelines(lines) f.close() except IOError as e: bsay(None, " Could not write story file: %s" % e) return status.push(0,"%s written successfully." % fn) else: bsay("File not found and not created: %s" % fn)
def readfile(fn,verbose = True): lines = [] if os.path.exists(os.path.abspath(fn)): try: with codecs.open(os.path.abspath(fn),'rU','utf-8') as f: lines = f.readlines() f.close() except IOError as e: if verbose: bsay(None, " Could not open file: %s" % e) status.push(0,"File read successfully: %s" % fn) else: if verbose: bsay(None,"File not found: %s" % fn) return lines
def getStateName(fileid): root = etree.Element("state") fn = os.path.join(config['realmdir'],fileid + ".xml") status.push(0,"reading city location from XML... '%s'" % fn) try: with codecs.open(fn,'rU','utf-8') as f: tree = etree.parse(f) f.close() root = tree.getroot() except IOError as e: print " Could not open configuration file: %s" % e if root.find("name") is None: return "" statename = root.find("name").text.strip() return statename
def storyDefault(target,rd): global config global status s = {} s = myStories(rd) if s == {} or len(s) != 1 or config['defaultstory'] == False: return k = s.keys() printPretty(k) v = k[0] m = "Single-story Realm. Setting stories value to %s. To prevent this, use the story editor to add stories to the realm, or change the setting in the options dialog." % v status.push(0,m) print m target.set_text(v) return
def getCityLoc(fileid): root = etree.Element("place") fn = os.path.join(config['realmdir'],"%s.xml" % fileid) status.push(0,"reading city location from XML... '%s'" % fn) try: with codecs.open(fn,'rU','utf-8') as f: tree = etree.parse(f) f.close() root = tree.getroot() except IOError as e: print " Could not open configuration file: %s" % e cityname = None statename = None statefile = None if root.find("name") is not None: cityname = root.find("name").text.strip() if root.find("state") is not None: statename = root.find("state").text.strip() if root.find("statefile") is not None: statefile = root.find("statefile").text.strip() return [cityname,statefile,statename]
def chooseCity(parent,target,tabs,scroll,data,statef,ar,stalts,title = ""): global status global cities city = recordSelectBox(None,statef,title,'c') if city and city[1] == "city": cityname = "" citlist = getCityList(0) cityf = validateFileid(citlist.get(statef,["",""])[1]) cityname = citlist.get(statef,["",""])[0] statename = citlist.get(statef,["","",""])[2] try: cityname = cities[city[0]]['info']['name'][0] cities[city[0]]['info']['state'] = [statename,True] cities[city[0]]['info']['statefile'] = [statef,True] cities[city[0]]['info']['loc'] = [cityname,True] cities[city[0]]['info']['locfile'] = [cityf,True] cities[city[0]]['changed'] = True saveThisC(parent,city[0]) # reloadPlaceTab(place[0]) # TODO: Write a function like this except KeyError: # placename = getPlaceNameFromID(place[0]) cityname = askBox("?"," Please type the city name that goes with %s" % city[0],"Name",subtext=" I tried to load this from memory, but you\ndon't have %s open. Without it open, I can't\nsynchronize its city and state values.\n This requirement prevents unintentional\nchanges to your place records." % city[0]) # Maybe some day, I'll make this grab the placename from the file, and automatically load its record for updating if cityname == "": status.push(0,"Registering place in %s cancelled" % cityf) return False packCity(target,scroll,data,statef,city[0],cityname,tabs,True,ar,stalts) status.push(0,"Registered %s in %s" % (city[1],statef)) return True else: status.push(0,"Registering place in %s cancelled" % statef) return False
def displayCity(callingWidget, fileid, tabrow): global cities ctalts = [] ar = gtk.Label() warnme = False if cities.get(fileid, None): tab = cities[fileid].get("tab") if tab is not None: warnme = True if not config["duplicatetabs"]: status.push(0, "'%s' is Already open. Switching to existing tab instead of loading..." % fileid) tabrow.set_current_page(tab) for i in range(len(tabrow)): if fileid == tabrow.get_tab_label_text(tabrow.get_nth_page(i)): tabrow.set_current_page(i) return # No need to load again. If revert needed, use a different function else: cities[fileid] = {} cities[fileid]["info"] = loadCity(fileid) cities[fileid]["changed"] = False cities[fileid]["cat"] = "c" displayStage1( tabrow, fileid, "c", saveThisC, showCity, preClose, displayCity, ar, ctalts ) # creates tabrow.vbox and tabrow.vbox.ftabs, et al tabrow.vbox.connect("destroy", tabdestroyed, fileid) tabrow.labeli = gtk.Label("Information") tabrow.vbox.ftabs.infpage = displayStage2(tabrow.vbox.ftabs, tabrow.labeli) tabrow.labelm = gtk.Label("Milestones") tabrow.vbox.ftabs.milepage = displayStage2(tabrow.vbox.ftabs, tabrow.labelm) if config["debug"] > 2: print "Loading " + tabrow.get_tab_label_text(tabrow.vbox) ar.show() ar.set_alignment(0.5, 0.5) setRuletext(ar, len(ctalts)) tabrow.vbox.pack_end(ar, 0, 0, 2) initCinfo(tabrow.vbox.ftabs.infpage, fileid, tabrow, ar, ctalts) initCmile(tabrow.vbox.ftabs.milepage, fileid, tabrow, ar, ctalts) tabrow.set_current_page(tabrow.page_num(tabrow.vbox)) cities[fileid]["tab"] = tabrow.page_num(tabrow.vbox)
def displayPlace(callingWidget,fileid, tabrow): global places plalts = [] ar = gtk.Label() warnme = False if places.get(fileid,None): tab = places[fileid].get("tab") if tab is not None: warnme = True if not config['duplicatetabs']: status.push(0,"'" + fileid + "' is Already open. Switching to existing tab instead of loading...") tabrow.set_current_page(tab) for i in range(len(tabrow)): if fileid == tabrow.get_tab_label_text(tabrow.get_nth_page(i)): tabrow.set_current_page(i) return # No need to load again. If revert needed, use a different function else: L = loadPlace(fileid) places[fileid] = {} places[fileid]['info'] = L[0] places[fileid]['relat'] = L[1] places[fileid]['changed'] = False places[fileid]['cat'] = 'l' displayStage1(tabrow,fileid,'l',saveThisL,showPlace,preClose,displayPlace,ar,plalts) tabrow.vbox.connect("destroy",tabdestroyed,fileid) tabrow.labeli = gtk.Label("Information") tabrow.labelr = gtk.Label("Connections") tabrow.vbox.ftabs.infpage = displayStage2(tabrow.vbox.ftabs,tabrow.labeli) tabrow.vbox.ftabs.relpage = displayStage2(tabrow.vbox.ftabs,tabrow.labelr) if config['debug'] > 2: print "Loading " + tabrow.get_tab_label_text(tabrow.vbox) ar.show() ar.set_alignment(0.5,0.5) setRuletext(ar,len(plalts)) tabrow.vbox.pack_end(ar,0,0,2) initLinfo(tabrow.vbox.ftabs.infpage, fileid,ar,plalts) initLrels(tabrow.vbox.ftabs.relpage, fileid,tabrow,ar,plalts) tabrow.set_current_page(tabrow.page_num(tabrow.vbox)) places[fileid]["tab"] = tabrow.page_num(tabrow.vbox)
def saveXMLtree(tree,category,fileid): out = "" if config['debug'] > 6: printPretty(etree.tostring(tree),True,True) try: out = etree.tostring(tree,pretty_print=True) except TypeError: # for me, previous line results in "unexpected keyword argument 'pretty_print'" out = xmlout.prettyXML(tree) start = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<?xml-stylesheet type=\"text/xsl\" href=\"" start += os.path.join(config['xslurl'],"%s.xsl" % category) start += "\"?>\n<!DOCTYPE person SYSTEM \"%s%s.dtd\">\n" % (config['dtdurl'],category) finaloutput = start + out if config['debug'] > 0: print finaloutput fn = os.path.join(os.path.abspath(config['realmdir']),fileid + ".xml") try: with codecs.open(fn,'wU','UTF-8') as f: f.write(finaloutput) f.close() except IOError as e: message = "The file %s could not be saved: %s" % (fn,e) common.bsay("?",message) status.push(0,message) return False return True
def displayState(callingWidget,fileid, tabrow): global states stalts = [] ar = gtk.Label() warnme = False if states.get(fileid,None): tab = states[fileid].get("tab") if tab is not None: warnme = True if not config['duplicatetabs']: status.push(0,"'" + fileid + "' is Already open. Switching to existing tab instead of loading...") tabrow.set_current_page(tab) for i in range(len(tabrow)): if fileid == tabrow.get_tab_label_text(tabrow.get_nth_page(i)): tabrow.set_current_page(i) return # No need to load again. If revert needed, use a different function else: states[fileid] = {} states[fileid]['info'] = loadState(fileid) states[fileid]['changed'] = False states[fileid]['cat'] = 's' displayStage1(tabrow,fileid,'s',saveThisS,showState,preClose,displayState,ar,stalts) # creates tabrow.vbox and tabrow.vbox.ftabs, et al tabrow.vbox.connect("destroy",tabdestroyed,fileid) tabrow.labeli = gtk.Label("Information") tabrow.vbox.ftabs.infpage = displayStage2(tabrow.vbox.ftabs,tabrow.labeli) tabrow.labelm = gtk.Label("Milestones") tabrow.vbox.ftabs.milepage = displayStage2(tabrow.vbox.ftabs,tabrow.labelm) if config['debug'] > 2: print "Loading " + tabrow.get_tab_label_text(tabrow.vbox) ar.show() ar.set_alignment(0.5,0.5) setRuletext(ar,len(stalts)) tabrow.vbox.pack_end(ar,0,0,2) initSinfo(tabrow.vbox.ftabs.infpage, fileid,tabrow,ar,stalts) initSmile(tabrow.vbox.ftabs.milepage, fileid,tabrow,ar,stalts) tabrow.set_current_page(tabrow.page_num(tabrow.vbox)) states[fileid]["tab"] = tabrow.page_num(tabrow.vbox)
def choosePlace(parent, target, tabs, scroll, data, cityf, ar, ctalts, title=""): global status global places place = recordSelectBox(None, cityf, title, "l") if place and place[1] == "place": placename = "" citlist = getCityList(0) statef = validateFileid(citlist.get(cityf, ["", ""])[1]) cityname = citlist.get(cityf, ["", ""])[0] statename = citlist.get(cityf, ["", "", ""])[2] try: placename = places[place[0]]["info"]["name"][0] places[place[0]]["info"]["state"] = [statename, True] places[place[0]]["info"]["statefile"] = [statef, True] places[place[0]]["info"]["loc"] = [cityname, True] places[place[0]]["info"]["locfile"] = [cityf, True] places[place[0]]["changed"] = True saveThisL(parent, place[0]) # reloadPlaceTab(place[0]) # TODO: Write a function like this except KeyError: # placename = getPlaceNameFromID(place[0]) placename = askBox( None, " Please type the location name that goes with %s" % place[0], "Name", subtext=" I tried to load this from memory, but you\ndon't have %s open. Without it open, I can't\nsynchronize its city and state values.\n This requirement prevents unintentional\nchanges to your place records." % place[0], ) # Maybe some day, I'll make this grab the placename from the file, and automatically load its record for updating if placename == "": status.push(0, "Registering place in %s cancelled" % cityf) return False packPlace(target, scroll, data, cityf, place[0], placename, tabs, True, ar, ctalts) status.push(0, "Registered %s in %s" % (place[1], cityf)) return True else: status.push(0, "Registering place in %s cancelled" % cityf) return False
def loadState(fileid): """Given an id (filename) matching an XML file in the appropriate directory, loads the tree from the file and pushes its data into a dictionary. """ dinf = {} root = etree.Element("state") text = None statename = "" statefile = "" # TODO: put this in a global variable, and make a function to populate it from the DTD. tags = ["name","start","scue","end","ecue","aspects","update"] for tag in tags: dinf[tag] = ["",False] dinf['cities'] = {} dinf['m'] = {} dinf['m']['events'] = {} dinf['aspects'] = {} if not idExists(fileid): status.push(0,"new state created... '%s'" % fileid) return dinf statefile = fileid fn = os.path.join(config['realmdir'],"%s.xml" % fileid) status.push(0,"loading state from XML... '%s'" % fn) try: with codecs.open(fn,'rU','utf-8') as f: tree = etree.parse(f) f.close() root = tree.getroot() except IOError as e: print "c: Could not open configuration file: %s" % e ir = 0 for i in range(len(root)): if root[i].tag is not None: if root[i].tag == "city": if len(root[i]) > 0: node = "" node = root[i].find("file") if node.text: node = node.text.strip() node = common.validateFileid(node) dinf['cities'][node] = {} for j in root[i]: if j.tag and j.text and j.tag != "file": dinf['cities'][node][j.tag] = [j.text.strip(),False] if config['debug'] > 3: printPretty(dinf['cities'][node]) else: if config['debug'] > 0: print "Invalid city tag:" for c in root[i]: print c.tag + ': ' + c.text, else: # no relat length if config['debug'] > 0: print "Empty city tag." elif root[i].tag == "events": if len(root[i]) > 0: nodes = root[i] for node in nodes: k = str(len(dinf['m']['events'])) dinf['m']['events'][k] = {} for j in node: if j.tag and j.text: dinf['m']['events'][k][j.tag] = [j.text.strip(),False] else: if config['debug'] > 0: print "Invalid milestone tag:" for c in node: print c.tag + ': ' + c.text, if config['debug'] > 3: printPretty(dinf['m']['events']) else: # no relat length if config['debug'] > 0: print "Empty milestone tag." elif root[i].tag == "aspects": if len(root[i]) > 0: nodes = root[i] for node in nodes: k = str(len(dinf['aspects'])) dinf['aspects'][k] = {} if node.tag and node.text: dinf['aspects'][k] = [node.text.strip(),False] else: if config['debug'] > 0: print "Invalid aspects tag:" print node.tag + ': ' + node.text, else: # no aspects length if config['debug'] > 0: print "Empty aspects tag." elif root[i].text is not None: dinf[root[i].tag] = [root[i].text.strip(), False] if config['debug'] > 2: print str(i) + " ", statename = dinf.get("name","") if len(statename) > 1: pushLoc(statefile,statename) return dinf
def loadPlace(fileid): """Given an id (filename) matching an XML file in the appropriate directory, loads the tree from the file and pushes its data into two dictionaries, which it returns as a tuple. """ dinf = {} drel = {} root = etree.Element("place") text = None city = "" cityf = "" state = "" statef = "" placename = "" # TODO: put this in a global variable, and make a function to populate it from the DTD. tags = ["commonname","name","start","scue","end","ecue","stories","mention","desc","address","loc","locfile","state","statefile","note", "relat","update"] tags.remove("note") tags.remove("relat") tags.append("file") for tag in tags: dinf[tag] = ["",False] # if no relations or notes, leave blank dinf['aspects'] = {} if not idExists(fileid): status.push(0,"new place created... '%s'" % fileid) return (dinf,drel) fn = os.path.join(config['realmdir'],"%s.xml" % fileid) status.push(0,"loading place from XML... '%s'" % fn) try: with codecs.open(fn,'rU','utf-8') as f: tree = etree.parse(f) f.close() root = tree.getroot() except IOError as e: print " Could not open place file: %s" % e ir = 0 for i in range(len(root)): if root[i].tag is not None: if root[i].tag == "relat": node = "" try: node = root[i].find("file").text.strip() except AttributeError: common.bsay("?","XML formatting error in %s! Probably an empty relat tag." % fileid) node = common.validateFileid(node) drel[node] = {} for j in root[i]: if j.tag == "events": if not drel[node].get('events'): drel[node]['events'] = {} for k in j: stone = str(len(drel[node]['events'])) drel[node]['events'][stone] = {} for m in k: if m.tag and m.text: drel[node]['events'][stone][m.tag] = [m.text.strip(),False] else: # elif j.tag != "file": if j.tag and j.text: drel[node][j.tag] = [j.text.strip(),False] if config['debug'] > 3: print drel[node] elif root[i].tag == "note": # print ",", if not dinf.get("notes"): dinf['notes'] = {} x = str(len(dinf['notes'])) dinf['notes'][x] = {} try: dinf['notes'][x]['content'] = [root[i].find("content").text.strip(),False] except AttributeError: del dinf['notes'][x] if dinf['notes'].get(x): dinf['notes'][x]['date'] = [root[i].find("date").text.strip(),False] # elif root[i].tag == "formocc": # print ",", elif root[i].tag == "aspects": if len(root[i]) > 0: nodes = root[i] for node in nodes: k = str(len(dinf['aspects'])) dinf['aspects'][k] = {} if node.tag and node.text: dinf['aspects'][k] = [node.text.strip(),False] else: if config['debug'] > 0: print "Invalid aspects tag:" print node.tag + ': ' + node.text, else: # no aspects length if config['debug'] > 0: print "Empty aspects tag." elif root[i].text is not None: if root[i].tag == "statefile": statef = root[i].text.strip() statef = common.validateFileid(statef) if statef is None: statef = "" elif root[i].tag == "state": state = root[i].text.strip() elif root[i].tag == "locfile": cityf = root[i].text.strip() cityf = common.validateFileid(cityf) if cityf is None: cityf = "" elif root[i].tag == "loc": city = root[i].text.strip() elif root[i].tag == "name": placename = root[i].text.strip() dinf[root[i].tag] = [root[i].text.strip(), False] if config['debug'] > 2: print str(i) + " ", if len(statef) > 0 and len(cityf) > 0: pushLoc(statef,state,cityf,city,fileid,placename) return (dinf,drel)
def loadPerson(fileid): """Given an id (filename) matching an XML file in the appropriate directory, loads the tree from the file and pushes its data into two dictionaries, which it returns as a tuple. """ dinf = {} drel = {} root = etree.Element("person") text = None # TODO: put this in a global variable, and make a function to populate it from the DTD. tags = ["commonname", "ctitle", "gname", "mname", "fname", "nname", "nameorder", "gender", "bday", "dday", "stories", "mention", "appear1ch", "appear1wr", "conflict", "leadrel", "bodytyp", "age", "skin", "eyes", "hair", "dmarks", "dress", "attposs", "asmell", "personality", "speech", "formocc", "currocc", "strength", "weak", "mole", "hobby", "misc", "ethnic", "origin", "backstory", "residence", "minchar", "talent", "abil", "sgoal", "other", "relat", "aspects", "update"] tags.remove("currocc") tags.remove("formocc") tags.remove("relat") tags.append("file") for tag in tags: dinf[tag] = ["",False] dinf['currocc'] = {} dinf['currocc']['pos'] = ["",False] dinf['formocc'] = {} dinf['formocc']['pos'] = ["",False] dinf['aspects'] = {} events = {} events['0'] = {} events['0']['date'] = ["",False] events['0']['event'] = ["",False] dinf['currocc']['events'] = events dinf['formocc']['events'] = events if not idExists(fileid): status.push(0,"new person created... '%s'" % fileid) return (dinf,drel) fn = os.path.join(config['realmdir'],fileid + ".xml") status.push(0,"loading person from XML... '%s'" % fn) try: with codecs.open(fn,'rU','utf-8') as f: tree = etree.parse(f) f.close() root = tree.getroot() except IOError as e: print " Could not open configuration file: %s" % e ir = 0 for i in range(len(root)): if root[i].tag is not None: if root[i].tag == "relat": if len(root[i]) > 0: node = "" node = root[i].find("file") if node is not None and node.text: node = node.text.strip() node = common.validateFileid(node) drel[node] = {} for j in root[i]: if j.tag == "events": if not drel[node].get('events'): drel[node]['events'] = {} for k in j: stone = str(len(drel[node]['events'])) drel[node]['events'][stone] = {} for m in k: if m.tag and m.text: drel[node]['events'][stone][m.tag] = [m.text.strip(),False] else: # elif j.tag != "file": if j.tag and j.text: drel[node][j.tag] = [j.text.strip(),False] if config['debug'] > 3: print drel[node] else: if config['debug'] > 0: print "Invalid relat tag:" for c in root[i]: print c.tag else: # no relat length if config['debug'] > 0: print "Empty relat tag." elif root[i].tag == "currocc": # print ",", dinf['currocc'] = {} try: dinf['currocc']['pos'] = [root[i].find("pos").text.strip(),False] except AttributeError: del dinf['currocc'] if dinf.get('currocc'): events = {} if len(root[i]) > 1: for j in root[i]: if j.tag is not None: if j.tag == "events": for k in j: if k.tag == "mstone": le = str(len(events)) events[le] = {} events[le]['date'] = ["",False] events[le]['event'] = ["",False] for m in k: if m.tag and m.text: events[le][m.tag] = [m.text.strip(),False] else: events['0'] = {} events['0']['date'] = ["",False] events['0']['event'] = ["",False] dinf['currocc']['events'] = events else: dinf['currocc'] = {} dinf['currocc']['pos'] = ["",False] events = {} events['0'] = {} events['0']['date'] = ["",False] events['0']['event'] = ["",False] dinf['currocc']['events'] = events elif root[i].tag == "formocc": # print ",", dinf['formocc'] = {} try: dinf['formocc']['pos'] = [root[i].find("pos").text.strip(),False] except AttributeError: del dinf['formocc'] if dinf.get('formocc'): events = {} if len(root[i]) > 1: for j in root[i]: if j.tag is not None: if j.tag == "events": for k in j: if k.tag == "mstone": le = str(len(events)) events[le] = {} events[le]['date'] = ["",False] events[le]['event'] = ["",False] for m in k: if m.tag and m.text: events[le][m.tag] = [m.text.strip(),False] else: events['0'] = {} events['0']['date'] = ["",False] events['0']['event'] = ["",False] dinf['formocc']['events'] = events else: dinf['formocc'] = {} dinf['formocc']['pos'] = ["",False] events = {} events['0'] = {} events['0']['date'] = ["",False] events['0']['event'] = ["",False] dinf['formocc']['events'] = events elif root[i].tag == "aspects": if len(root[i]) > 0: nodes = root[i] for node in nodes: k = str(len(dinf['aspects'])) dinf['aspects'][k] = {} if node.tag and node.text: dinf['aspects'][k] = [node.text.strip(),False] else: if config['debug'] > 0: print "Invalid aspects tag:" print node.tag + ': ' + node.text, else: # no aspects length if config['debug'] > 0: print "Empty aspects tag." elif root[i].text is not None: # print ".", dinf[root[i].tag] = [root[i].text.strip(), False] if config['debug'] > 2: print str(i) + " ", # print str(dinf) return (dinf,drel)
def reloadThis(caller,closer,opener,fileid,mark,target): status.push(0,"Attempting to reload %s..." % fileid) closer(caller,fileid,mark) opener(caller,fileid,target)
def main(self): status.push(0,"Load a record from the menus to begin.") if config['startnewperson']: getFileid(self,self.tabs) gtk.main()
def optionSetter(caller,parent = "?",canskip = True): global config global status options = {} factor = 0.80 if parent == "?": parent = mainWin print "parent: %s" % parent title = "Setting Options" optbox = gtk.Dialog(title,parent,gtk.DIALOG_MODAL | gtk.DIALOG_DESTROY_WITH_PARENT,(gtk.STOCK_CANCEL,gtk.RESPONSE_CANCEL,gtk.STOCK_APPLY,gtk.RESPONSE_APPLY,gtk.STOCK_OK,gtk.RESPONSE_OK)) if not canskip: optbox.get_action_area().get_children()[2].set_sensitive(False) # buttons seem to number right to left applyBut = optbox.get_action_area().get_children()[1] applyBut.set_sensitive(False) # optbox.get_action_area().get_children()[0].set_sensitive(False) if not config.get("nowindowstore"): optbox.set_geometry_hints(None,int(config['size'][0] * factor),int(config['size'][1] * (factor - 0.05))) # optbox.set_decorated(False) sw = gtk.VBox() sw.show() sw.set_border_width(10) scroll = gtk.ScrolledWindow() scroll.show() scroll.set_policy(gtk.POLICY_NEVER,gtk.POLICY_AUTOMATIC) scroll.add_with_viewport(sw) optbox.vbox.add(scroll) rf = config['realmfile'] if rf == "": rf = "<unspecified>" label = gtk.Label("Realm-specific Options for %s" % rf) label.show() sw.pack_start(label,False,False,7) row = gtk.HBox() label = gtk.Label("Name of this realm/setting/world: ") e = gtk.Entry() e.show() e.set_text(config.get("realmname","Unnamed Realm")) optbox.set_title("Setting Options - %s" % e.get_text()) e.connect("changed",setOpt,None,options,"realmname",2) e.connect("changed",mayApply,applyBut) e.connect("focus-in-event",scrollOnTab,scroll) row.show() label.show() row.pack_start(label,False,False,2) row.pack_start(e,True,True,2) sw.pack_start(row) row = gtk.HBox() label = gtk.Label("Realm Directory: ") e = gtk.Entry() e.show() e.set_text(config.get("realmdir","")) e.connect("changed",setOpt,None,options,"realmdir",2) e.connect("changed",mayApply,applyBut) e.connect("focus-in-event",scrollOnTab,scroll) row.show() label.show() row.pack_start(label,False,False,2) row.pack_start(e,True,True,2) sw.pack_start(row) cb = gtk.CheckButton("Family name comes first (Eastern style names)") cb.set_active(config.get("familyfirst",False)) cb.connect("toggled",setOpt,None,options,"familyfirst",1) cb.connect("toggled",mayApply,applyBut) cb.connect("focus-in-event",scrollOnTab,scroll) cb.show() sw.pack_start(cb) cb = gtk.CheckButton("Use middle/maiden names") cb.set_active(config.get("usemiddle",True)) cb.connect("toggled",setOpt,None,options,"usemiddle",1) cb.connect("toggled",mayApply,applyBut) cb.connect("focus-in-event",scrollOnTab,scroll) cb.show() sw.pack_start(cb) sqlbox = gtk.Frame("SQL Options") xmlbox = gtk.Frame("XML Options") formats = ["xml","sql"] forms = [("informat","Input format"),("outformat","Output format")] for key in forms: label = key[1] key = key[0] group = None row = gtk.HBox() row.show() label = gtk.Label("%s:" % label) label.show() row.pack_start(label,False,False,2) c = gtk.combo_box_new_text() selected = -1 options[key] = config.get(key,"xml") i = 0 for f in formats: if f == options.get(key): selected = i c.append_text(f) i += 1 c.set_active(selected) c.connect("changed",setOpt,None,options,key,3) c.connect("changed",mayApply,applyBut) c.connect("changed",toggleBoxes,None,sqlbox,xmlbox,options) c.connect("move-active",setOpt,options,key,3) c.connect("move-active",toggleBoxes,sqlbox,xmlbox,options) c.connect("focus",scrollOnTab,scroll) c.connect("focus-in-event",scrollOnTab,scroll) c.show() row.pack_start(c,False,False,2) sw.pack_start(row) sw.pack_start(sqlbox) sw.pack_start(xmlbox) toggleBoxes(None,None,sqlbox,xmlbox,options) xb = gtk.VBox() xb.show() xmlbox.add(xb) sb = gtk.VBox() sb.show() sqlbox.add(sb) ####### SQL box options label = gtk.Label("SQL input/output is not yet implemented.\nPlease use XML for the time being.") label.show() sb.pack_start(label) ####### XML box options cb = gtk.CheckButton("Include empty tags when saving XML files") cb.set_active(config.get("printemptyXMLtags",False)) cb.connect("toggled",setOpt,None,options,"printemptyXMLtags",1) cb.connect("toggled",mayApply,applyBut) cb.connect("focus-in-event",scrollOnTab,scroll) cb.show() xb.pack_start(cb) row = gtk.HBox() label = gtk.Label("DTDs are found in this directory: ") e = gtk.Entry() e.show() e.set_text(config.get("dtddir","")) e.connect("changed",setOpt,None,options,"dtddir",2) e.connect("changed",mayApply,applyBut) e.connect("focus-in-event",scrollOnTab,scroll) row.show() label.show() row.pack_start(label,False,False,2) row.pack_start(e,True,True,2) xb.pack_start(row) row = gtk.HBox() label = gtk.Label("URL for DTD in XML files: ") e = gtk.Entry() e.show() e.set_text(config.get("dtdurl","")) e.connect("changed",setOpt,None,options,"dtdurl",2) e.connect("changed",mayApply,applyBut) e.connect("focus-in-event",scrollOnTab,scroll) row.show() label.show() row.pack_start(label,False,False,2) row.pack_start(e,True,True,2) xb.pack_start(row) row = gtk.HBox() label = gtk.Label("URL for XSL files in XML: ") e = gtk.Entry() e.show() e.set_text(config.get("xslurl","")) e.connect("changed",setOpt,None,options,"xslurl",2) e.connect("changed",mayApply,applyBut) e.connect("focus-in-event",scrollOnTab,scroll) row.show() label.show() row.pack_start(label,False,False,2) row.pack_start(e,True,True,2) xb.pack_start(row) row = gtk.HBox() label = gtk.Label("Century assumed for 2-digit years: ") test = gtk.Label("Test dates:") test.show() a = gtk.Adjustment(int(config.get("century",1900)/100),-499,500) s1 = gtk.SpinButton(a,1.0,0) s1.set_increments(1,10) s1.show() s1.connect("value-changed",setOpt,None,options,"century",5) s1.connect("value-changed",mayApply,applyBut) s1.connect("focus-in-event",scrollOnTab,scroll) row.show() label.show() row.pack_start(label,False,False,2) row.pack_start(s1,False,False,2) label = gtk.Label("Split year: ") label.show() a = gtk.Adjustment(int(config.get("centbreak",77)),0,99) s2 = gtk.SpinButton(a,1.0,0) s2.set_increments(1,10) s2.show() s2.connect("value-changed",setOpt,None,options,"centbreak",4) s2.connect("value-changed",mayApply,applyBut) s2.connect("focus-in-event",scrollOnTab,scroll) row.pack_start(label,False,False,2) row.pack_start(s2,True,True,2) setDates(None,s1,s2,test) s2.connect("value-changed",setDates,s1,s2,test) s1.connect("value-changed",setDates,s1,s2,test) sw.pack_start(row) sw.pack_start(test,True,True,2) cb = gtk.CheckButton("Show only calculated date") cb.set_active(config.get("hideage",True)) cb.connect("toggled",setOpt,None,options,"hideage",1) cb.connect("toggled",mayApply,applyBut) cb.connect("focus-in-event",scrollOnTab,scroll) cb.show() sw.pack_start(cb) row = gtk.HBox() label = gtk.Label("Date for age calculations: ") label.show() e = gtk.Entry() e.set_text(config.get("agedate","06/08/10b")) e.connect("changed",setOpt,None,options,"agedate",2) e.connect("changed",mayApply,applyBut) e.show() row.show() row.pack_start(label,0,0,2) row.pack_start(e,1,1,2) placeCalendarButton(None,row,e,None,[],nomark=True) sw.pack_start(row,0,0,2) row = gtk.HBox() label = gtk.Label("Expert: Style for dates in this realm: ") e = gtk.Entry() e.show() e.set_text(config.get("datestyle","%y/%m/%db")) e.connect("changed",setOpt,None,options,"datestyle",2) e.connect("changed",mayApply,applyBut) e.connect("focus-in-event",scrollOnTab,scroll) row.show() label.show() row.pack_start(label,False,False,2) row.pack_start(e,True,True,2) sw.pack_start(row) row = gtk.HBox() label = gtk.Label("Background color for a changed field: ") e = gtk.Entry() e.show() e.set_text(config.get("altcolor","#FFFFFF")) e.connect("changed",setOpt,None,options,"altcolor",2) e.connect("changed",mayApply,applyBut) e.connect("changed",setBack,e,gtk.STATE_NORMAL) setBack(None,e,gtk.STATE_NORMAL) e.connect("focus-in-event",scrollOnTab,scroll) b = gtk.Button("Choose Color") b.connect("clicked",selColor,e) b.show() row.show() label.show() row.pack_start(label,False,False,2) row.pack_start(e,True,True,2) row.pack_start(b,False,False,2) sw.pack_start(row) row = gtk.HBox() label = gtk.Label("Background color for a changed field after save: ") e = gtk.Entry() e.show() e.set_text(config.get("savecolor","#FFFFFF")) e.connect("changed",setOpt,None,options,"savecolor",2) e.connect("changed",mayApply,applyBut) e.connect("changed",setBack,e,gtk.STATE_NORMAL) setBack(None,e,gtk.STATE_NORMAL) e.connect("focus-in-event",scrollOnTab,scroll) b = gtk.Button("Choose Color") b.connect("clicked",selColor,e) b.show() row.show() label.show() row.pack_start(label,False,False,2) row.pack_start(e,True,True,2) row.pack_start(b,False,False,2) sw.pack_start(row) cb = gtk.CheckButton("Use list files for this realm") cb.set_active(config.get("uselistfile",True)) cb.connect("toggled",setOpt,None,options,"uselistfile",1) cb.connect("toggled",mayApply,applyBut) cb.connect("focus-in-event",scrollOnTab,scroll) cb.show() sw.pack_start(cb) cb = gtk.CheckButton("Use only realm-defined relationships, not free text") cb.set_active(config.get("specialrelsonly",True)) cb.connect("toggled",setOpt,None,options,"specialrelsonly",1) cb.connect("toggled",mayApply,applyBut) cb.connect("focus-in-event",scrollOnTab,scroll) cb.show() sw.pack_start(cb) row = gtk.HBox() row.show() label = gtk.Label("Story List Format:") label.show() row.pack_start(label,False,False,2) c = gtk.combo_box_new_text() selected = -1 options["showstories"] = config.get("showstories","idlist") i = 0 formats = ["idlist","titlelist"] for f in formats: if f == options.get("showstories"): selected = i c.append_text(f) i += 1 c.set_active(selected) c.connect("changed",setOpt,None,options,"showstories",3) c.connect("changed",mayApply,applyBut) c.connect("move-active",setOpt,options,"showstories",3) c.connect("move-active",mayApply,applyBut) c.connect("focus",scrollOnTab,scroll) c.connect("focus-in-event",scrollOnTab,scroll) c.show() row.pack_start(c,False,False,2) sw.pack_start(row) cb = gtk.CheckButton("If only one story, set default Story List value") cb.set_active(config.get("defaultstory",True)) cb.connect("toggled",setOpt,None,options,"defaultstory",1) cb.connect("toggled",mayApply,applyBut) cb.connect("focus-in-event",scrollOnTab,scroll) cb.show() sw.pack_start(cb) ####### >>>>>>> label = gtk.Label("Program-wide Options") label.show() sw.pack_start(label,False,False,7) cb = gtk.CheckButton("Don't store window size/position") cb.set_active(config.get("nowindowstore",False)) cb.connect("toggled",setOpt,None,options,"nowindowstore",1) cb.connect("toggled",mayApply,applyBut) cb.connect("focus-in-event",scrollOnTab,scroll) cb.show() sw.pack_start(cb) cb = gtk.CheckButton("Accept realm-specific options in the config file") cb.set_active(config.get("rlmincfg",False)) cb.connect("toggled",setOpt,None,options,"rlmincfg",1) cb.connect("toggled",mayApply,applyBut) cb.connect("focus-in-event",scrollOnTab,scroll) cb.show() sw.pack_start(cb) cb = gtk.CheckButton("Opening a new person file at startup") cb.set_active(config.get("startnewperson",False)) cb.connect("toggled",setOpt,None,options,"startnewperson",1) cb.connect("toggled",mayApply,applyBut) cb.connect("focus-in-event",scrollOnTab,scroll) cb.show() sw.pack_start(cb) cb = gtk.CheckButton("Allow opening duplicate tabs") cb.set_active(config.get("duplicatetabs",False)) cb.connect("toggled",setOpt,None,options,"duplicatetabs",1) cb.connect("toggled",mayApply,applyBut) cb.connect("focus-in-event",scrollOnTab,scroll) cb.show() sw.pack_start(cb) cb = gtk.CheckButton("Save the active realm file on exit") cb.set_active(config.get("saverealm",False)) cb.connect("toggled",setOpt,None,options,"saverealm",1) cb.connect("toggled",mayApply,applyBut) cb.connect("focus-in-event",scrollOnTab,scroll) cb.show() sw.pack_start(cb) row = gtk.HBox() row.show() label = gtk.Label("Load this realm automatically:") label.show() row.pack_start(label,False,False,2) d = gtk.Label() d.set_text(config.get("loadrealm","")) d.show() row.pack_start(d,True,True,2) but = gtk.Button("Select Realm") but.connect("clicked",chooseRealm,d,options) but.connect("clicked",mayApply,applyBut) but.show() row.pack_start(but,False,False,2) sw.pack_start(row) row = gtk.HBox() row.show() label = gtk.Label("Likerealm handling:") label.show() row.pack_start(label,False,False,2) c = gtk.combo_box_new_text() selected = -1 options["matchlike"] = config.get("matchlike",2) i = 0 formats = ["Keep likerealm and track which options are from where","Keep likerealm and save only options that differ","Save all options and omit likerealm"] for f in formats: if i == options.get("matchlike"): selected = i c.append_text(f) i += 1 if selected != -1: c.set_active(selected) c.connect("changed",setOpt,None,options,"matchlike",1) c.connect("changed",mayApply,applyBut) c.connect("move-active",setOpt,options,"matchlike",1) c.connect("move-active",mayApply,applyBut) c.connect("focus",scrollOnTab,scroll) c.connect("focus-in-event",scrollOnTab,scroll) c.show() row.pack_start(c,False,False,2) sw.pack_start(row) resp = 0 while resp not in [-6,-5]: resp = optbox.run() if resp == -10: t = "Options applied." print t status.push(0,t) copyOpts(options) if options.get("realmname") is not None: updateTitle() options = {} optbox.set_title("Setting Options - %s" % config.get("realmname","Unnamed Realm")) applyBut.set_sensitive(False) if resp == -6: t = "Cancelled" print t status.push(0,t) optbox.destroy() return elif resp == -5: t = "Options accepted." print t status.push(0,t) optbox.destroy() copyOpts(options) if options.get("realmname") is not None: updateTitle() # saveConfig() # saveRealm() return
def loadRealm(self,fn): global config global worldList status.push(0,"Destroying menus...") clearMenus() status.push(0,"Clearing worldList...") worldList = {} # clear worldList status.push(0,"Reloading config...") backends.killRealmOpts() status.push(0,"Loading realm...") config.update(backends.loadRealm(fn)) status.push(0,"Populating realm...") common.updateTitle() backends.populateWorld() status.push(0,"Building menus...") doMenus(self) pass
def killListFile(caller = None): os.remove(os.path.join(os.path.abspath(config['realmdir']),"myrealm.cfg")) say("WorldList destroyed!") global status status.push(0,"WorldList destroyed!")