def new_project(): """ 所有的命令都存储在属性'cmd',参数都存储在属性’argv‘中,全局配置的词典key使用'cmd',方便解析 没有参数的命令,使能把命令的存储参数设置为True 有参数的命令,使能就存储参数 :return: """ doc = QDomDocument("PyQt5Helper.prj") # QDomDocument类 instruction: QDomProcessingInstruction = doc.createProcessingInstruction("PyQt5Helper", "version={} " "encoding=\"UTF-8\"".format(version)) doc.appendChild(instruction) root: QDomElement = doc.createElement("PyQt5Helper.prj-config") # 创建general节点 doc.appendChild(root) # 1. 通用选项 item_list = project_item_dict.keys() for item in item_list: logging.debug(item) # general,generate_what item_element: QDomElement = doc.createElement(item) # 创建general节点 root.appendChild(item_element) item_dict = project_item_dict[item] # dist_path_cmd: ['./restore_dist', True, 'dist_path']}, for child_item in item_dict.keys(): # dist_path_cmd save_item = item_dict[child_item] e: QDomElement = doc.createElement(save_item[2]) # child tag item_element.appendChild(e) # --onedir,--onefile e.setAttribute("argv", save_item[0]) e.setAttribute("cmd", child_item) e.setAttribute("state", save_item[1]) return doc
def _write_history_file(self, date_str, snapshot_name='', rewind_snapshot=''): if not self.session.path: return ray.Err.NO_SESSION_OPEN file_path = self._get_history_full_path() xml = QDomDocument() try: history_file = open(file_path, 'r') xml.setContent(history_file.read()) history_file.close() except: pass if xml.firstChild().isNull(): SNS_xml = xml.createElement('SNAPSHOTS') xml.appendChild(SNS_xml) else: SNS_xml = xml.firstChild() snapshot_el = xml.createElement('Snapshot') snapshot_el.setAttribute('ref', date_str) snapshot_el.setAttribute('name', snapshot_name) snapshot_el.setAttribute('rewind_snapshot', rewind_snapshot) snapshot_el.setAttribute('session_name', self.session.name) snapshot_el.setAttribute('VERSION', ray.VERSION) for client in self.session.clients + self.session.trashed_clients: client_el = xml.createElement('client') client.write_xml_properties(client_el) client_el.setAttribute('client_id', client.client_id) for client_file_path in client.get_project_files(): base_path = client_file_path.replace("%s/" % self.session.path, '', 1) file_xml = xml.createElement('file') file_xml.setAttribute('path', base_path) client_el.appendChild(file_xml) snapshot_el.appendChild(client_el) SNS_xml.appendChild(snapshot_el) try: history_file = open(file_path, 'w') history_file.write(xml.toString()) history_file.close() except: return ray.Err.CREATE_FAILED return ray.Err.OK
def saveFile(self, executable, config_file, arguments_line, save_signal, no_save_level, stop_signal, wait_window): try: file = open(self.path, 'w') except BaseException: return if not save_signal: save_signal = 0 xml = QDomDocument() p = xml.createElement('RAY-PROXY') p.setAttribute('VERSION', ray.VERSION) p.setAttribute('executable', executable) p.setAttribute('arguments', arguments_line) p.setAttribute('config_file', config_file) p.setAttribute('save_signal', str(int(save_signal))) p.setAttribute('no_save_level', str(no_save_level)) p.setAttribute('stop_signal', str(int(stop_signal))) p.setAttribute('wait_window', wait_window) xml.appendChild(p) contents = "<?xml version='1.0' encoding='UTF-8'?>\n" contents += "<!DOCTYPE RAY-PROXY>\n" contents += xml.toString() file.write(contents) file.close() self.readFile()
def saveFile(): if not file_path: return for connection in connection_list: if not connection in saved_connections: saved_connections.append(connection) delete_list = [] # delete connection of the saved_connections # if its two ports are still presents and not connected for i in range(len(saved_connections)): if (portExists(saved_connections[i][0], PORT_MODE_OUTPUT) and portExists(saved_connections[i][1], PORT_MODE_INPUT)): if not saved_connections[i] in connection_list: delete_list.append(i) delete_list.reverse() for i in delete_list: saved_connections.__delitem__(i) try: file = open(file_path, 'w') except: sys.stderr.write('unable to write file %s\n' % file_path) app.quit() return xml = QDomDocument() p = xml.createElement('RAY-JACKPATCH') for con in saved_connections: ct = xml.createElement('connection') ct.setAttribute('from', con[0]) ct.setAttribute('to', con[1]) p.appendChild(ct) xml.appendChild(p) file.write(xml.toString()) file.close() NSMServer.saveReply() setDirtyClean()
def get_layer_symbology(layer): doc = QDomDocument(QDomImplementation().createDocumentType("qgis", "http://mrcc.com/qgis.dtd", "SYSTEM")) rootNode = doc.createElement("qgis") doc.appendChild(rootNode) errorMsg = '' ctx = QgsReadWriteContext() layer.writeSymbology(rootNode, doc, errorMsg, ctx) return doc.toByteArray()
def installACL(self, idacl): """ Crea un nuevo fichero "acl.xml" y lo almacena sustituyendo el anterior, en el caso de que exista. @param idacl Identificador del registro de la tabla "flacls" a utilizar para crear "acl.xml". """ util = FLUtil() doc = QDomDocument("ACL") root = doc.createElement("ACL") doc.appendChild(root) name = doc.createElement("name") root.appendChild(name) n = doc.createTextNode(idacl) name.appendChild(n) q = FLSqlQuery() q.setTablesList("flacs") q.setSelect("idac,tipo,nombre,iduser,idgroup,degroup,permiso") q.setFrom("flacs") q.setWhere("idacl='%s'" % idacl) q.setOrderBy("prioridad DESC, tipo") q.setForwarOnly(True) if q.exec_(): step = 0 progress = util.ProgressDialog( util.tr("Instalando control de acceso..."), None, q.size(), None, None, True) progress.setCaption(util.tr("Instalando ACL")) progress.setMinimumDuration(0) progress.setProgress(++step) while q.next(): self.makeRule(q, doc) progress.setProgress(++step) self.database().managerModules().setContent( "acl.xml", "sys", doc.toString())
def installACL(self, idacl): """ Crea un nuevo fichero "acl.xml" y lo almacena sustituyendo el anterior, en el caso de que exista. @param idacl Identificador del registro de la tabla "flacls" a utilizar para crear "acl.xml". """ util = FLUtil() doc = QDomDocument("ACL") root = doc.createElement("ACL") doc.appendChild(root) name = doc.createElement("name") root.appendChild(name) n = doc.createTextNode(idacl) name.appendChild(n) q = FLSqlQuery() q.setTablesList("flacs") q.setSelect("idac,tipo,nombre,iduser,idgroup,degroup,permiso") q.setFrom("flacs") q.setWhere("idacl='%s'" % idacl) q.setOrderBy("prioridad DESC, tipo") q.setForwarOnly(True) if q.exec_(): step = 0 progress = util.ProgressDialog( util.tr("Instalando control de acceso..."), None, q.size(), None, None, True) progress.setCaption(util.tr("Instalando ACL")) progress.setMinimumDuration(0) progress.setProgress(++step) while q.next(): self.makeRule(q, doc) progress.setProgress(++step) from pineboolib.pnconrolsfactory import aqApp aqApp.db().managerModules().setContent("acl.xml", "sys", doc.toString())
def updateRasterToken(self, layer, uri): """ http://gis.stackexchange.com/questions/62610/changing-data-source-of-layer-in-qgis """ XMLDocument = QDomDocument("style") XMLMapLayers = QDomElement() XMLMapLayers = XMLDocument.createElement("maplayers") XMLMapLayer = QDomElement() XMLMapLayer = XMLDocument.createElement("maplayer") layer.writeLayerXML(XMLMapLayer,XMLDocument) # modify DOM element with new layer reference XMLMapLayer.firstChildElement("datasource").firstChild().setNodeValue( uri ) XMLMapLayers.appendChild(XMLMapLayer) XMLDocument.appendChild(XMLMapLayers) # reload layer definition layer.readLayerXML(XMLMapLayer) layer.reload() # apply to canvas and legend self.iface.actionDraw().trigger() self.iface.legendInterface().refreshLayerSymbology(layer)
def make_bookmark(self, spath): if self.written: return contents = self._get_contents() if not contents: #we won't write a file for kde5 if file doesn't already exists return url = pathlib.Path(spath).as_uri() xml = QDomDocument() xml.setContent(contents) content = xml.documentElement() if content.tagName() != 'xbel': return node = content.firstChild() while not node.isNull(): el = node.toElement() if el.tagName() == 'bookmark': if el.attribute('href') == url: #bookmark already exists return node = node.nextSibling() bk = xml.createElement('bookmark') bk.setAttribute('href', url) title = xml.createElement('title') title_text = xml.createTextNode(os.path.basename(spath)) title.appendChild(title_text) bk.appendChild(title) content.appendChild(bk) if self._print_contents(xml.toString()): self.written = True
def toXml(self, obj_, includeChildren=True, includeComplexTypes=False): xml_ = QDomDocument() if not obj_: return xml_ e = xml_.createElement(type(obj_).__name__) e.setAttribute("class", type(obj_).__name__) xml_.appendChild(e) _meta = obj_.metaObject() num = _meta.propertyCount() i = 0 _p_properties = [] while i < num: mp = _meta.property(i) if mp.name() in _p_properties: i += 1 continue _p_properties.append(mp.name()) val = getattr(obj_, mp.name(), None) try: val = val() except: pass if val is None: i += 1 continue val = str(val) if not val and not includeComplexTypes: i += 1 continue e.setAttribute(mp.name(), val) i += 1 if includeChildren == True: for child in obj_.children(): itd = self.toXml(child, includeChildren, includeComplexTypes) xml_.firstChild().appendChild(itd.firstChild()) return xml_
def _get_xml(self): xml = QDomDocument() file_exists = False if os.path.exists(self._bookmarks_memory): try: file = open(self._bookmarks_memory, 'r') xml.setContent(file.read()) file_exists = True except: try: os.path.remove(self._bookmarks_memory) except: return None if not file_exists: bms_xml = xml.createElement('Bookmarks') xml.appendChild(bms_xml) return xml
def cloneItem(item, composition_dest, x_0, y_0): ref_point = item.referencePoint() item.setReferencePoint(QgsLayoutItem.UpperLeft) original_x = item.pagePos().x() original_y = item.pagePos().y() final_x = original_x + x_0 final_y = original_y + y_0 # Create doc xml doc = QDomDocument('Clipboard') element = doc.createElement('Copied items') context = QgsReadWriteContext() item.writeXml(element, doc, context) # Add doc xml composition_dest.addItemsFromXml(element, doc, context, QPointF(final_x, final_y)) composition_dest.itemById(item.id()).attemptMove( QgsLayoutPoint(final_x, final_y)) composition_dest.itemById(item.id()).refresh() item.setReferencePoint(ref_point)
def write_xml(configDictionary={}, pageData=[], pagesLocationList=[], locationBasic=str(), locationStandAlone=str(), projectUrl=str()): acbfGenreList = [ "science_fiction", "fantasy", "adventure", "horror", "mystery", "crime", "military", "real_life", "superhero", "humor", "western", "manga", "politics", "caricature", "sports", "history", "biography", "education", "computer", "religion", "romance", "children", "non-fiction", "adult", "alternative", "other", "artbook" ] acbfAuthorRolesList = [ "Writer", "Adapter", "Artist", "Penciller", "Inker", "Colorist", "Letterer", "Cover Artist", "Photographer", "Editor", "Assistant Editor", "Translator", "Other", "Designer" ] document = QDomDocument() root = document.createElement("ACBF") root.setAttribute("xmlns", "http://www.acbf.info/xml/acbf/1.1") document.appendChild(root) emphasisStyle = {} strongStyle = {} if "acbfStyles" in configDictionary.keys(): stylesDictionary = configDictionary.get("acbfStyles", {}) emphasisStyle = stylesDictionary.get("emphasis", {}) strongStyle = stylesDictionary.get("strong", {}) styleString = "\n" tabs = " " for key in sorted(stylesDictionary.keys()): style = stylesDictionary.get(key, {}) if key == "emphasis" or key == "strong": styleClass = key + " {\n" elif key == "speech": styleClass = "text-area {\n" elif key == "general": styleClass = "* {\n" elif key == "inverted": styleClass = "text-area[inverted=\"true\"] {\n" else: styleClass = "text-area[type=\"" + key + "\"] {\n" styleString += tabs + styleClass if "color" in style.keys(): styleString += tabs + tabs + "color:" + style["color"] + ";\n" if "font" in style.keys(): fonts = style["font"] genericfont = style.get("genericfont", "sans-serif") if isinstance(fonts, list): styleString += tabs + tabs + "font-family:\"" + str( "\", \"").join(fonts) + "\", " + genericfont + ";\n" else: styleString += tabs + tabs + "font-family:\"" + fonts + "\", " + genericfont + ";\n" if "bold" in style.keys(): if style["bold"]: styleString += tabs + tabs + "font-weight: bold;\n" if "ital" in style.keys(): if style["ital"]: styleString += tabs + tabs + "font-style: italic;\n" else: styleString += tabs + tabs + "font-style: normal;\n" styleString += tabs + "}\n" style = document.createElement("style") style.setAttribute("type", "text/css") style.appendChild(document.createTextNode(styleString)) root.appendChild(style) meta = document.createElement("meta-data") translationFolder = configDictionary.get("translationLocation", "translations") fullTranslationPath = os.path.join(projectUrl, translationFolder) poParser = po_parser.po_file_parser(fullTranslationPath, True) bookInfo = document.createElement("book-info") if "authorList" in configDictionary.keys(): for authorE in range(len(configDictionary["authorList"])): author = document.createElement("author") authorDict = configDictionary["authorList"][authorE] if "first-name" in authorDict.keys(): authorN = document.createElement("first-name") authorN.appendChild( document.createTextNode(str(authorDict["first-name"]))) author.appendChild(authorN) if "last-name" in authorDict.keys(): authorN = document.createElement("last-name") authorN.appendChild( document.createTextNode(str(authorDict["last-name"]))) author.appendChild(authorN) if "initials" in authorDict.keys(): authorN = document.createElement("middle-name") authorN.appendChild( document.createTextNode(str(authorDict["initials"]))) author.appendChild(authorN) if "nickname" in authorDict.keys(): authorN = document.createElement("nickname") authorN.appendChild( document.createTextNode(str(authorDict["nickname"]))) author.appendChild(authorN) if "homepage" in authorDict.keys(): authorN = document.createElement("home-page") authorN.appendChild( document.createTextNode(str(authorDict["homepage"]))) author.appendChild(authorN) if "email" in authorDict.keys(): authorN = document.createElement("email") authorN.appendChild( document.createTextNode(str(authorDict["email"]))) author.appendChild(authorN) if "role" in authorDict.keys(): if str(authorDict["role"]).title() in acbfAuthorRolesList: author.setAttribute("activity", str(authorDict["role"])) if "language" in authorDict.keys(): author.setAttribute( "lang", str(authorDict["language"]).replace("_", "-")) bookInfo.appendChild(author) bookTitle = document.createElement("book-title") if "title" in configDictionary.keys(): bookTitle.appendChild( document.createTextNode(str(configDictionary["title"]))) else: bookTitle.appendChild( document.createTextNode(str("Comic with no Name"))) bookInfo.appendChild(bookTitle) extraGenres = [] if "genre" in configDictionary.keys(): genreListConf = configDictionary["genre"] if isinstance(configDictionary["genre"], dict): genreListConf = configDictionary["genre"].keys() for genre in genreListConf: genreModified = str(genre).lower() genreModified.replace(" ", "_") if genreModified in acbfGenreList: bookGenre = document.createElement("genre") bookGenre.appendChild( document.createTextNode(str(genreModified))) if isinstance(configDictionary["genre"], dict): genreMatch = configDictionary["genre"][genreModified] if genreMatch > 0: bookGenre.setAttribute("match", str(genreMatch)) bookInfo.appendChild(bookGenre) else: extraGenres.append(genre) if "characters" in configDictionary.keys(): character = document.createElement("characters") for name in configDictionary["characters"]: char = document.createElement("name") char.appendChild(document.createTextNode(str(name))) character.appendChild(char) bookInfo.appendChild(character) annotation = document.createElement("annotation") if "summary" in configDictionary.keys(): paragraphList = str(configDictionary["summary"]).split("\n") for para in paragraphList: p = document.createElement("p") p.appendChild(document.createTextNode(str(para))) annotation.appendChild(p) else: p = document.createElement("p") p.appendChild( document.createTextNode( str("There was no summary upon generation of this file."))) annotation.appendChild(p) bookInfo.appendChild(annotation) keywords = document.createElement("keywords") stringKeywordsList = [] for key in extraGenres: stringKeywordsList.append(str(key)) if "otherKeywords" in configDictionary.keys(): for key in configDictionary["otherKeywords"]: stringKeywordsList.append(str(key)) if "format" in configDictionary.keys(): for key in configDictionary["format"]: stringKeywordsList.append(str(key)) keywords.appendChild(document.createTextNode( ", ".join(stringKeywordsList))) bookInfo.appendChild(keywords) coverpageurl = "" coverpage = document.createElement("coverpage") if "pages" in configDictionary.keys(): if "cover" in configDictionary.keys(): pageList = [] pageList = configDictionary["pages"] coverNumber = max([pageList.index(configDictionary["cover"]), 0]) image = document.createElement("image") if len(pagesLocationList) >= coverNumber: coverpageurl = pagesLocationList[coverNumber] image.setAttribute("href", os.path.basename(coverpageurl)) coverpage.appendChild(image) bookInfo.appendChild(coverpage) if "language" in configDictionary.keys(): language = document.createElement("languages") textlayer = document.createElement("text-layer") textlayer.setAttribute( "lang", str(configDictionary["language"]).replace("_", "-")) textlayer.setAttribute("show", "false") textlayerNative = document.createElement("text-layer") textlayerNative.setAttribute( "lang", str(configDictionary["language"]).replace("_", "-")) textlayerNative.setAttribute("show", "true") language.appendChild(textlayer) language.appendChild(textlayerNative) translationComments = {} for lang in poParser.get_translation_list(): textlayer = document.createElement("text-layer") textlayer.setAttribute("lang", lang) textlayer.setAttribute("show", "true") language.appendChild(textlayer) translationComments[lang] = [] translation = poParser.get_entry_for_key( "@meta-title " + configDictionary["title"], lang).get("trans", None) if translation is not None: bookTitleTr = document.createElement("book-title") bookTitleTr.setAttribute("lang", lang) bookTitleTr.appendChild(document.createTextNode(translation)) bookInfo.insertAfter(bookTitleTr, bookTitle) translation = poParser.get_entry_for_key( "@meta-summary " + configDictionary["summary"], lang).get("trans", None) if translation is not None: annotationTr = document.createElement("annotation") annotationTr.setAttribute("lang", lang) paragraph = document.createElement("p") paragraph.appendChild(document.createTextNode(translation)) annotationTr.appendChild(paragraph) bookInfo.insertAfter(annotationTr, annotation) translation = poParser.get_entry_for_key( "@meta-keywords " + ", ".join(configDictionary["otherKeywords"]), lang).get("trans", None) if translation is not None: keywordsTr = document.createElement("keywords") keywordsTr.setAttribute("lang", lang) keywordsTr.appendChild(document.createTextNode(translation)) bookInfo.insertAfter(keywordsTr, keywords) bookInfo.appendChild(language) bookTitle.setAttribute( "lang", str(configDictionary["language"]).replace("_", "-")) annotation.setAttribute( "lang", str(configDictionary["language"]).replace("_", "-")) keywords.setAttribute( "lang", str(configDictionary["language"]).replace("_", "-")) if "databaseReference" in configDictionary.keys(): database = document.createElement("databaseref") dbRef = configDictionary["databaseReference"] database.setAttribute("dbname", dbRef.get("name", "")) if "type" in dbRef.keys(): database.setAttribute("type", dbRef["type"]) database.appendChild(document.createTextNode(dbRef.get("entry", ""))) bookInfo.appendChild(database) if "seriesName" in configDictionary.keys(): sequence = document.createElement("sequence") sequence.setAttribute("title", configDictionary["seriesName"]) if "seriesVolume" in configDictionary.keys(): sequence.setAttribute("volume", str(configDictionary["seriesVolume"])) if "seriesNumber" in configDictionary.keys(): sequence.appendChild( document.createTextNode(str(configDictionary["seriesNumber"]))) else: sequence.appendChild(document.createTextNode(str(0))) bookInfo.appendChild(sequence) contentrating = document.createElement("content-rating") if "rating" in configDictionary.keys(): contentrating.appendChild( document.createTextNode(str(configDictionary["rating"]))) else: contentrating.appendChild(document.createTextNode(str("Unrated."))) if "ratingSystem" in configDictionary.keys(): contentrating.setAttribute("type", configDictionary["ratingSystem"]) bookInfo.appendChild(contentrating) if "readingDirection" in configDictionary.keys(): readingDirection = document.createElement("reading-direction") if configDictionary["readingDirection"] is "rightToLeft": readingDirection.appendChild(document.createTextNode(str("RTL"))) else: readingDirection.appendChild(document.createTextNode(str("LTR"))) bookInfo.appendChild(readingDirection) meta.appendChild(bookInfo) publisherInfo = document.createElement("publish-info") if "publisherName" in configDictionary.keys(): publisherName = document.createElement("publisher") publisherName.appendChild( document.createTextNode(str(configDictionary["publisherName"]))) publisherInfo.appendChild(publisherName) if "publishingDate" in configDictionary.keys(): publishingDate = document.createElement("publish-date") publishingDate.setAttribute("value", configDictionary["publishingDate"]) publishingDate.appendChild( document.createTextNode( QDate.fromString(configDictionary["publishingDate"], Qt.ISODate).toString( Qt.SystemLocaleLongDate))) publisherInfo.appendChild(publishingDate) if "publisherCity" in configDictionary.keys(): publishCity = document.createElement("city") publishCity.appendChild( document.createTextNode(str(configDictionary["publisherCity"]))) publisherInfo.appendChild(publishCity) if "isbn-number" in configDictionary.keys(): publishISBN = document.createElement("isbn") publishISBN.appendChild( document.createTextNode(str(configDictionary["isbn-number"]))) publisherInfo.appendChild(publishISBN) license = str(configDictionary.get("license", "")) if license.isspace() is False and len(license) > 0: publishLicense = document.createElement("license") publishLicense.appendChild(document.createTextNode(license)) publisherInfo.appendChild(publishLicense) meta.appendChild(publisherInfo) documentInfo = document.createElement("document-info") # TODO: ACBF apparently uses first/middle/last/nick/email/homepage for the document author too... # The following code compensates for me not understanding this initially. if "acbfAuthor" in configDictionary.keys(): if isinstance(configDictionary["acbfAuthor"], list): for e in configDictionary["acbfAuthor"]: acbfAuthor = document.createElement("author") authorDict = e if "first-name" in authorDict.keys(): authorN = document.createElement("first-name") authorN.appendChild( document.createTextNode(str(authorDict["first-name"]))) acbfAuthor.appendChild(authorN) if "last-name" in authorDict.keys(): authorN = document.createElement("last-name") authorN.appendChild( document.createTextNode(str(authorDict["last-name"]))) acbfAuthor.appendChild(authorN) if "initials" in authorDict.keys(): authorN = document.createElement("middle-name") authorN.appendChild( document.createTextNode(str(authorDict["initials"]))) acbfAuthor.appendChild(authorN) if "nickname" in authorDict.keys(): authorN = document.createElement("nickname") authorN.appendChild( document.createTextNode(str(authorDict["nickname"]))) acbfAuthor.appendChild(authorN) if "homepage" in authorDict.keys(): authorN = document.createElement("home-page") authorN.appendChild( document.createTextNode(str(authorDict["homepage"]))) acbfAuthor.appendChild(authorN) if "email" in authorDict.keys(): authorN = document.createElement("email") authorN.appendChild( document.createTextNode(str(authorDict["email"]))) acbfAuthor.appendChild(authorN) if "language" in authorDict.keys(): acbfAuthor.setAttribute( "lang", str(authorDict["language"]).replace("_", "-")) documentInfo.appendChild(acbfAuthor) else: acbfAuthor = document.createElement("author") acbfAuthorNick = document.createElement("nickname") acbfAuthorNick.appendChild( document.createTextNode(str(configDictionary["acbfAuthor"]))) acbfAuthor.appendChild(acbfAuthorNick) documentInfo.appendChild(acbfAuthor) else: acbfAuthor = document.createElement("author") acbfAuthorNick = document.createElement("nickname") acbfAuthorNick.appendChild(document.createTextNode(str("Anon"))) acbfAuthor.appendChild(acbfAuthorNick) documentInfo.appendChild(acbfAuthor) acbfDate = document.createElement("creation-date") now = QDate.currentDate() acbfDate.setAttribute("value", now.toString(Qt.ISODate)) acbfDate.appendChild( document.createTextNode(str(now.toString(Qt.SystemLocaleLongDate)))) documentInfo.appendChild(acbfDate) if "acbfSource" in configDictionary.keys(): acbfSource = document.createElement("source") acbfSourceP = document.createElement("p") acbfSourceP.appendChild( document.createTextNode(str(configDictionary["acbfSource"]))) acbfSource.appendChild(acbfSourceP) documentInfo.appendChild(acbfSource) if "acbfID" in configDictionary.keys(): acbfID = document.createElement("id") acbfID.appendChild( document.createTextNode(str(configDictionary["acbfID"]))) documentInfo.appendChild(acbfID) if "acbfVersion" in configDictionary.keys(): acbfVersion = document.createElement("version") acbfVersion.appendChild( document.createTextNode(str(configDictionary["acbfVersion"]))) documentInfo.appendChild(acbfVersion) if "acbfHistory" in configDictionary.keys(): if len(configDictionary["acbfHistory"]) > 0: acbfHistory = document.createElement("history") for h in configDictionary["acbfHistory"]: p = document.createElement("p") p.appendChild(document.createTextNode(str(h))) acbfHistory.appendChild(p) documentInfo.appendChild(acbfHistory) meta.appendChild(documentInfo) root.appendChild(meta) body = document.createElement("body") references = document.createElement("references") def figure_out_type(svg=QDomElement()): type = None skipList = ["speech", "emphasis", "strong", "inverted", "general"] if svg.attribute("text-anchor") == "middle" or svg.attribute( "text-align") == "center": if "acbfStyles" in configDictionary.keys(): stylesDictionary = configDictionary.get("acbfStyles", {}) for key in stylesDictionary.keys(): if key not in skipList: style = stylesDictionary.get(key, {}) font = style.get("font", "") if isinstance(fonts, list): if svg.attribute("family") in font: type = key elif svg.attribute("family") == font: type = key else: type = None elif svg.attribute("text-align") == "justified": type = "formal" else: type = "commentary" inverted = None #Figure out whether this is inverted colored text. if svg.hasAttribute("fill"): stylesDictionary = configDictionary.get("acbfStyles", {}) key = stylesDictionary.get("general", {}) regular = QColor(key.get("color", "#000000")) key = stylesDictionary.get("inverted", {}) invertedColor = QColor(key.get("color", "#FFFFFF")) textColor = QColor(svg.attribute("fill")) # Proceed to get luma for the three colors. lightnessR = (0.21 * regular.redF()) + ( 0.72 * regular.greenF()) + (0.07 * regular.blueF()) lightnessI = (0.21 * invertedColor.redF()) + ( 0.72 * invertedColor.greenF()) + (0.07 * invertedColor.blueF()) lightnessT = (0.21 * textColor.redF()) + ( 0.72 * textColor.greenF()) + (0.07 * textColor.blueF()) if lightnessI > lightnessR: if lightnessT > (lightnessI + lightnessR) * 0.5: inverted = "true" else: if lightnessT < (lightnessI + lightnessR) * 0.5: inverted = "true" return [type, inverted] listOfPageColors = [] for p in range(0, len(pagesLocationList)): page = pagesLocationList[p] imageFile = QImage() imageFile.load(page) imageRect = imageFile.rect().adjusted(0, 0, -1, -1) pageColor = findDominantColor([ imageFile.pixelColor(imageRect.topLeft()), imageFile.pixelColor(imageRect.topRight()), imageFile.pixelColor(imageRect.bottomRight()), imageFile.pixelColor(imageRect.bottomLeft()) ]) listOfPageColors.append(pageColor) language = "en" if "language" in configDictionary.keys(): language = str(configDictionary["language"]).replace("_", "-") textLayer = document.createElement("text-layer") textLayer.setAttribute("lang", language) data = pageData[p] transform = data["transform"] frameList = [] listOfTextColors = [] for v in data["vector"]: boundingBoxText = [] listOfBoundaryColors = [] for point in v["boundingBox"]: offset = QPointF(transform["offsetX"], transform["offsetY"]) pixelPoint = QPointF(point.x() * transform["resDiff"], point.y() * transform["resDiff"]) newPoint = pixelPoint - offset x = max( 0, min(imageRect.width(), int(newPoint.x() * transform["scaleWidth"]))) y = max( 0, min(imageRect.height(), int(newPoint.y() * transform["scaleHeight"]))) listOfBoundaryColors.append(imageFile.pixelColor(x, y)) pointText = str(x) + "," + str(y) boundingBoxText.append(pointText) mainColor = findDominantColor(listOfBoundaryColors) if "text" in v.keys(): textArea = document.createElement("text-area") textArea.setAttribute("points", " ".join(boundingBoxText)) # TODO: Rotate will require proper global transform api as transform info is not written intotext. #textArea.setAttribute("text-rotation", str(v["rotate"])) svg = QDomDocument() svg.setContent(v["text"]) figureOut = figure_out_type(svg.documentElement()) type = figureOut[0] inverted = figureOut[1] paragraph = QDomDocument() paragraph.appendChild(paragraph.createElement("p")) parseTextChildren(paragraph, svg.documentElement(), paragraph.documentElement(), emphasisStyle, strongStyle) textArea.appendChild(paragraph.documentElement()) textArea.setAttribute("bgcolor", mainColor.name()) if type is not None: textArea.setAttribute("type", type) if inverted is not None: textArea.setAttribute("inverted", inverted) textLayer.appendChild(textArea) else: f = {} f["points"] = " ".join(boundingBoxText) frameList.append(f) listOfTextColors.append(mainColor) textLayer.setAttribute("bgcolor", findDominantColor(listOfTextColors).name()) textLayerList = document.createElement("trlist") for lang in poParser.get_translation_list(): textLayerTr = document.createElement("text-layer") textLayerTr.setAttribute("lang", lang) for i in range(len(data["vector"])): d = data["vector"] v = d[i] boundingBoxText = [] for point in v["boundingBox"]: offset = QPointF(transform["offsetX"], transform["offsetY"]) pixelPoint = QPointF(point.x() * transform["resDiff"], point.y() * transform["resDiff"]) newPoint = pixelPoint - offset x = int(newPoint.x() * transform["scaleWidth"]) y = int(newPoint.y() * transform["scaleHeight"]) pointText = str(x) + "," + str(y) boundingBoxText.append(pointText) if "text" in v.keys(): textArea = document.createElement("text-area") textArea.setAttribute("points", " ".join(boundingBoxText)) # TODO: Rotate will require proper global transform api as transform info is not written intotext. #textArea.setAttribute("text-rotation", str(v["rotate"])) svg = QDomDocument() svg.setContent(v["text"]) figureOut = figure_out_type(svg.documentElement()) type = figureOut[0] inverted = figureOut[1] string = re.sub("\<\/*?text.*?\>", '', str(v["text"])) string = re.sub("\s+?", " ", string) translationEntry = poParser.get_entry_for_key(string, lang) string = translationEntry.get("trans", string) svg.setContent("<text>" + string + "</text>") paragraph = QDomDocument() paragraph.appendChild(paragraph.createElement("p")) parseTextChildren(paragraph, svg.documentElement(), paragraph.documentElement(), emphasisStyle, strongStyle) if "translComment" in translationEntry.keys(): key = translationEntry["translComment"] listOfComments = [] listOfComments = translationComments[lang] index = 0 if key in listOfComments: index = listOfComments.index(key) + 1 else: listOfComments.append(key) index = len(listOfComments) translationComments[lang] = listOfComments refID = "-".join(["tn", lang, str(index)]) anchor = document.createElement("a") anchor.setAttribute("href", "#" + refID) anchor.appendChild(document.createTextNode("*")) paragraph.documentElement().appendChild(anchor) textArea.appendChild(paragraph.documentElement()) textLayerTr.appendChild(textArea) if type is not None: textArea.setAttribute("type", type) if inverted is not None: textArea.setAttribute("inverted", inverted) textArea.setAttribute("bgcolor", listOfTextColors[i].name()) if textLayerTr.hasChildNodes(): textLayerTr.setAttribute( "bgcolor", findDominantColor(listOfTextColors).name()) textLayerList.appendChild(textLayerTr) if page is not coverpageurl: pg = document.createElement("page") image = document.createElement("image") image.setAttribute("href", os.path.basename(page)) pg.appendChild(image) if "acbf_title" in data["keys"]: title = document.createElement("title") title.setAttribute("lang", language) title.appendChild(document.createTextNode(str(data["title"]))) pg.appendChild(title) for lang in poParser.get_translation_list(): titleTrans = " " titlekey = "@page-title " + str(data["title"]) translationEntry = poParser.get_entry_for_key( titlekey, lang) titleTrans = translationEntry.get("trans", titleTrans) if titleTrans.isspace() is False: titleT = document.createElement("title") titleT.setAttribute("lang", lang) titleT.appendChild(document.createTextNode(titleTrans)) pg.appendChild(titleT) if "acbf_none" in data["keys"]: pg.setAttribute("transition", "none") if "acbf_blend" in data["keys"]: pg.setAttribute("transition", "blend") if "acbf_fade" in data["keys"]: pg.setAttribute("transition", "fade") if "acbf_horizontal" in data["keys"]: pg.setAttribute("transition", "scroll_right") if "acbf_vertical" in data["keys"]: pg.setAttribute("transition", "scroll_down") if textLayer.hasChildNodes(): pg.appendChild(textLayer) pg.setAttribute("bgcolor", pageColor.name()) for n in range(0, textLayerList.childNodes().size()): node = textLayerList.childNodes().at(n) pg.appendChild(node) for f in frameList: frame = document.createElement("frame") frame.setAttribute("points", f["points"]) pg.appendChild(frame) body.appendChild(pg) else: for f in frameList: frame = document.createElement("frame") frame.setAttribute("points", f["points"]) coverpage.appendChild(frame) coverpage.appendChild(textLayer) for n in range(0, textLayerList.childNodes().size()): node = textLayerList.childNodes().at(n) coverpage.appendChild(node) bodyColor = findDominantColor(listOfPageColors) body.setAttribute("bgcolor", bodyColor.name()) if configDictionary.get("includeTranslComment", False): for lang in translationComments.keys(): for key in translationComments[lang]: index = translationComments[lang].index(key) + 1 refID = "-".join(["tn", lang, str(index)]) ref = document.createElement("reference") ref.setAttribute("lang", lang) ref.setAttribute("id", refID) transHeaderStr = configDictionary.get("translatorHeader", "Translator's Notes") transHeaderStr = poParser.get_entry_for_key( "@meta-translator " + transHeaderStr, lang).get("trans", transHeaderStr) translatorHeader = document.createElement("p") translatorHeader.appendChild( document.createTextNode(transHeaderStr + ":")) ref.appendChild(translatorHeader) refPara = document.createElement("p") refPara.appendChild(document.createTextNode(key)) ref.appendChild(refPara) references.appendChild(ref) root.appendChild(body) if references.childNodes().size(): root.appendChild(references) f = open(locationBasic, 'w', newline="", encoding="utf-8") f.write(document.toString(indent=2)) f.close() success = True success = createStandAloneACBF(configDictionary, document, locationStandAlone, pagesLocationList) return success
class XmlSignBox(QPushButton): signed = pyqtSignal() def __init__(self, parent=None, xmlelement='QDomElement:None', index=0, edit=False): super().__init__(parent) self.element = xmlelement self.index = index self.edit = edit self.namelist = [] self.setStyleSheet("background-color: rgb(255, 0, 0);border:none;") width = int(self.element.attribute( "width")) * 7 if self.element.attribute("width") else 13 height = int(self.element.attribute( "height")) * 22 if self.element.attribute("height") else 22 self.resize(width, height) font = QFont() if self.element.hasAttribute("size"): try: font.setPointSize(float(self.element.attribute("size"))) except: pass self.setFont(font) self.clicked.connect(self.on_Clicked) self.qdom = QDomDocument() self.many = self.element.attribute("many") self.direction = self.element.attribute("direction") if self.many == '2': self.set_namelist() else: self.uid = self.element.firstChildElement("UserID") self.uname = self.element.firstChildElement("UserName") if self.uid.isNull(): self.uid = self.qdom.createElement('UserID') self.uid = self.element.appendChild(self.uid) if self.uname.isNull(): self.uname = self.qdom.createElement('UserName') self.uname = self.element.appendChild(self.uname) self.namelist.append( (self.uid.toElement(), self.uname.toElement())) # self.setText(self.uid.nodeValue() + ' ' + self.uname.nodeValue()) text = '' for item in self.namelist: text += item[0].text() + ' ' + item[1].text() if self.direction == '1' and self.many == '2': text += '\n' elif self.direction == '1' and self.many == '2': text += ' ' self.setText(text) def set_namelist(self): n = self.element.firstChildElement("UserID") while not n.isNull(): self.uid = n n = self.element.nextSibling() self.uname = n n = self.element.nextSibling() self.namelist.append((self.uid, self.uname)) def on_Clicked(self): # if not self.edit: dialog = SignModule() dialog.userchanged.connect(self.setusername) dialog.exec() def setusername(self, p_bool, p_str): clerkid, clerkname = p_str.split(' ') cid = self.qdom.createTextNode(clerkid) cname = self.qdom.createTextNode(clerkname) if self.many == '2': if p_bool: uid = self.qdom.createElement("UserID") uname = self.qdom.createElement("UserName") self.element.appendChild(uid) self.element.appendChild(uname) self.namelist.append((uid, uname)) uid.appendChild(cid) uname.appendChild(cname) else: for item in self.namelist[:]: if item[0].text() == clerkid and item[1].text( ) == clerkname: self.element.removeChild(item[0]) self.element.removeChild(item[1]) self.namelist.remove(item) else: self.uid.removeChild(self.uid.firstChild()) self.uname.removeChild(self.uname.firstChild()) self.uid.appendChild(cid) self.uname.appendChild(cname) text = '' for item in self.namelist: text += item[0].text() + ' ' + item[1].text() if self.direction == '1' and self.many == '2': text += '\n' elif self.direction == '0' and self.many == '2': text += ' ' self.setText(text) self.signed.emit() def mousePressEvent(self, event) -> None: if self.edit: event.ignore() else: super(XmlSignBox, self).mousePressEvent(event) def focusInEvent(self, event) -> None: if self.edit: self.setStyleSheet("background-color: rgb(0, 255, 255);") super(XmlSignBox, self).focusInEvent(event) def leave(self): if self.edit: self.setStyleSheet("")
def write_ncx_file(path, configDictionary, htmlFiles, listOfNavItems): tocDoc = QDomDocument() ncx = tocDoc.createElement("ncx") ncx.setAttribute("version", "2005-1") ncx.setAttribute("xmlns", "http://www.daisy.org/z3986/2005/ncx/") tocDoc.appendChild(ncx) tocHead = tocDoc.createElement("head") # NCX also has some meta values that are in the head. # They are shared with the opf metadata document. uuid = str(configDictionary["uuid"]) uuid = uuid.strip("{") uuid = uuid.strip("}") metaID = tocDoc.createElement("meta") metaID.setAttribute("content", uuid) metaID.setAttribute("name", "dtb:uid") tocHead.appendChild(metaID) metaDepth = tocDoc.createElement("meta") metaDepth.setAttribute("content", str(1)) metaDepth.setAttribute("name", "dtb:depth") tocHead.appendChild(metaDepth) metaTotal = tocDoc.createElement("meta") metaTotal.setAttribute("content", str(len(htmlFiles))) metaTotal.setAttribute("name", "dtb:totalPageCount") tocHead.appendChild(metaTotal) metaMax = tocDoc.createElement("meta") metaMax.setAttribute("content", str(len(htmlFiles))) metaMax.setAttribute("name", "dtb:maxPageNumber") tocHead.appendChild(metaDepth) ncx.appendChild(tocHead) docTitle = tocDoc.createElement("docTitle") text = tocDoc.createElement("text") if "title" in configDictionary.keys(): text.appendChild(tocDoc.createTextNode(str(configDictionary["title"]))) else: text.appendChild(tocDoc.createTextNode("Comic with no Name")) docTitle.appendChild(text) ncx.appendChild(docTitle) # The navmap is a table of contents. navmap = tocDoc.createElement("navMap") navPoint = tocDoc.createElement("navPoint") navPoint.setAttribute("id", "navPoint-1") navPoint.setAttribute("playOrder", "1") navLabel = tocDoc.createElement("navLabel") navLabelText = tocDoc.createElement("text") navLabelText.appendChild(tocDoc.createTextNode("Start")) navLabel.appendChild(navLabelText) navContent = tocDoc.createElement("content") navContent.setAttribute("src", os.path.relpath(htmlFiles[0], str(path))) navPoint.appendChild(navLabel) navPoint.appendChild(navContent) navmap.appendChild(navPoint) entry = 1 for fileName in listOfNavItems.keys(): entry += 1 navPointT = tocDoc.createElement("navPoint") navPointT.setAttribute("id", "navPoint-" + str(entry)) navPointT.setAttribute("playOrder", str(entry)) navLabelT = tocDoc.createElement("navLabel") navLabelTText = tocDoc.createElement("text") navLabelTText.appendChild( tocDoc.createTextNode(listOfNavItems[fileName])) navLabelT.appendChild(navLabelTText) navContentT = tocDoc.createElement("content") navContentT.setAttribute("src", os.path.relpath(fileName, str(path))) navPointT.appendChild(navLabelT) navPointT.appendChild(navContentT) navmap.appendChild(navPointT) ncx.appendChild(navmap) # The pages list on the other hand just lists all pages. pagesList = tocDoc.createElement("pageList") navLabelPages = tocDoc.createElement("navLabel") navLabelPagesText = tocDoc.createElement("text") navLabelPagesText.appendChild(tocDoc.createTextNode("Pages")) navLabelPages.appendChild(navLabelPagesText) pagesList.appendChild(navLabelPages) for i in range(len(htmlFiles)): pageTarget = tocDoc.createElement("pageTarget") pageTarget.setAttribute("type", "normal") pageTarget.setAttribute("id", "page-" + str(i)) pageTarget.setAttribute("value", str(i)) navLabelPagesTarget = tocDoc.createElement("navLabel") navLabelPagesTargetText = tocDoc.createElement("text") navLabelPagesTargetText.appendChild(tocDoc.createTextNode(str(i + 1))) navLabelPagesTarget.appendChild(navLabelPagesTargetText) pageTarget.appendChild(navLabelPagesTarget) pageTargetContent = tocDoc.createElement("content") pageTargetContent.setAttribute( "src", os.path.relpath(htmlFiles[i], str(path))) pageTarget.appendChild(pageTargetContent) pagesList.appendChild(pageTarget) ncx.appendChild(pagesList) # Save the document. docFile = open(str(Path(path / "toc.ncx")), 'w', newline="", encoding="utf-8") docFile.write(tocDoc.toString(indent=2)) docFile.close() return str(Path(path / "toc.ncx"))
class XmlExprBox(QLineEdit): def __init__(self, parent=None, xmlelement='QDomElement:None', index=0, edit=False): super().__init__(parent) self.element = xmlelement self.index = index self.edit = edit self.qdom = QDomDocument() self.wid = self.element.attribute("ID") self.value = 0 self.var_dict = dict() self.widget_dict = dict() # 后缀 self.subfix = self.element.firstChildElement("subfix") self.subfix_value = self.subfix.firstChild() # 公式 self.vars = self.element.firstChildElement("vars") self.vars_value = self.vars.firstChild() # 计算结果 self.expr = self.element.firstChildElement("expr") self.expr_value = self.expr.firstChild() # 初始化后缀、公式、计算结果 self.set_subfix() self.set_vars() self.set_expr() self.setReadOnly(True) # self.setFocusPolicy(Qt.StrongFocus) # self.setStyleSheet("background-color: rgb(85, 255, 255);margin:2 2;") width = int(self.element.attribute( "width")) * 7 if self.element.attribute("width") else 130 height = int(self.element.attribute( "height")) * 24 if self.element.attribute("height") else 24 self.resize(width, height) def set_subfix(self): if self.subfix.isNull(): self.subfix = self.qdom.createElement("subfix") self.subfix = self.element.appendChild(self.subfix) if self.subfix.firstChild().isNull(): self.subfix_value = self.qdom.createTextNode("") self.subfix_value = self.subfix.appendChild(self.subfix_value) def set_vars(self): if self.vars.isNull(): self.vars = self.qdom.createElement("vars") self.vars = self.element.appendChild(self.vars) if self.vars.firstChild().isNull(): self.vars_value = self.qdom.createTextNode("") self.vars_value = self.subfix.appendChild(self.vars_value) def set_expr(self): if self.expr.isNull(): self.expr = self.qdom.createElement("expr") self.expr = self.element.appendChild(self.expr) if self.expr.firstChild().isNull(): self.expr_value = self.qdom.createTextNode("") self.expr_value = self.subfix.appendChild(self.expr_value) def varToWidget(self, var, widgetOrValue: tuple): # widgetOrValue,包括2个值(flag,value) # 如果flag = 0,则为value # 如果flag = 1,则为widget if var not in self.var_dict: self.var_dict[var] = widgetOrValue def ChangedSlot(self, p_str): # widget = self.sender() # 可能会抛出ValueError # self.widget_dict[widget] = int(p_str) self.flush() def flush(self): formula = self.vars_value.nodeValue() expr = self.expr_value.nodeValue() try: for key, value in self.var_dict.items(): kind = value[0] wvalue = str(value[1].value if value[1].value != '' else 0) \ if kind else str(value[1]) try: if formula: formula = formula.replace(key, wvalue) except Exception as e: pass try: if expr: expr = expr.replace(key, wvalue) except Exception as e: pass expr = str(eval(expr, evalenv(self))) self.value = expr self.setText(formula + expr + self.subfix_value.nodeValue()) self.setStyleSheet("background-color: rgb(170, 255, 127);") except Exception as e: self.setToolTip("结果异常," + key + "的值异常") self.setStyleSheet("background-color: rgb(255, 255, 0);") def mousePressEvent(self, event) -> None: if self.edit: event.ignore() else: super(XmlExprBox, self).mousePressEvent(event) def focusInEvent(self, event) -> None: if self.edit: self.setStyleSheet("background-color: rgb(0, 255, 255);") super(XmlExprBox, self).focusInEvent(event) def leave(self): if self.edit: self.flush()
def write_region_nav_file(path, configDictionary, htmlFiles, regions=[]): navDoc = QDomDocument() navRoot = navDoc.createElement("html") navRoot.setAttribute("xmlns", "http://www.w3.org/1999/xhtml") navRoot.setAttribute("xmlns:epub", "http://www.idpf.org/2007/ops") navDoc.appendChild(navRoot) head = navDoc.createElement("head") title = navDoc.createElement("title") title.appendChild(navDoc.createTextNode("Region Navigation")) head.appendChild(title) navRoot.appendChild(head) body = navDoc.createElement("body") navRoot.appendChild(body) nav = navDoc.createElement("nav") nav.setAttribute("epub:type", "region-based") nav.setAttribute("prefix", "ahl: http://idpf.org/epub/vocab/ahl") body.appendChild(nav) # Let's write the panels and balloons down now. olPanels = navDoc.createElement("ol") for region in regions: if region["type"] == "panel": pageName = os.path.relpath(region["page"], str(path)) print("accessing panel") li = navDoc.createElement("li") li.setAttribute("epub:type", "panel") anchor = navDoc.createElement("a") bounds = region["points"] anchor.setAttribute( "href", pageName + "#xywh=percent:" + str(bounds.x()) + "," + str(bounds.y()) + "," + str(bounds.width()) + "," + str(bounds.height())) if len(region["primaryColor"]) > 0: primaryC = navDoc.createElement("meta") primaryC.setAttribute("property", "ahl:primary-color") primaryC.setAttribute("content", region["primaryColor"]) anchor.appendChild(primaryC) li.appendChild(anchor) olBalloons = navDoc.createElement("ol") """ The region nav spec specifies that we should have text-areas/balloons as a refinement on the panel. For each panel, we'll check if there's balloons/text-areas inside, and we'll do that by checking whether the center point is inside the panel because some comics have balloons that overlap the gutters. """ for balloon in regions: if balloon["type"] == "text" and balloon["page"] == region[ "page"] and bounds.contains( balloon["points"].center()): liBalloon = navDoc.createElement("li") liBalloon.setAttribute("epub:type", "text-area") anchorBalloon = navDoc.createElement("a") BBounds = balloon["points"] anchorBalloon.setAttribute( "href", pageName + "#xywh=percent:" + str(BBounds.x()) + "," + str(BBounds.y()) + "," + str(BBounds.width()) + "," + str(BBounds.height())) liBalloon.appendChild(anchorBalloon) olBalloons.appendChild(liBalloon) if olBalloons.hasChildNodes(): li.appendChild(olBalloons) olPanels.appendChild(li) nav.appendChild(olPanels) navFile = open(str(Path(path / "region-nav.xhtml")), 'w', newline="", encoding="utf-8") navFile.write(navDoc.toString(indent=2)) navFile.close() return str(Path(path / "region-nav.xhtml"))
def write_nav_file(path, configDictionary, htmlFiles, listOfNavItems): navDoc = QDomDocument() navRoot = navDoc.createElement("html") navRoot.setAttribute("xmlns", "http://www.w3.org/1999/xhtml") navRoot.setAttribute("xmlns:epub", "http://www.idpf.org/2007/ops") navDoc.appendChild(navRoot) head = navDoc.createElement("head") title = navDoc.createElement("title") title.appendChild(navDoc.createTextNode("Table of Contents")) head.appendChild(title) navRoot.appendChild(head) body = navDoc.createElement("body") navRoot.appendChild(body) # The Table of Contents toc = navDoc.createElement("nav") toc.setAttribute("epub:type", "toc") oltoc = navDoc.createElement("ol") li = navDoc.createElement("li") anchor = navDoc.createElement("a") anchor.setAttribute("href", os.path.relpath(htmlFiles[0], str(path))) anchor.appendChild(navDoc.createTextNode("Start")) li.appendChild(anchor) oltoc.appendChild(li) for fileName in listOfNavItems.keys(): li = navDoc.createElement("li") anchor = navDoc.createElement("a") anchor.setAttribute("href", os.path.relpath(fileName, str(path))) anchor.appendChild(navDoc.createTextNode(listOfNavItems[fileName])) li.appendChild(anchor) oltoc.appendChild(li) toc.appendChild(oltoc) body.appendChild(toc) # The Pages List. pageslist = navDoc.createElement("nav") pageslist.setAttribute("epub:type", "page-list") olpages = navDoc.createElement("ol") entry = 1 for i in range(len(htmlFiles)): li = navDoc.createElement("li") anchor = navDoc.createElement("a") anchor.setAttribute("href", os.path.relpath(htmlFiles[1], str(path))) anchor.appendChild(navDoc.createTextNode(str(i))) li.appendChild(anchor) olpages.appendChild(li) pageslist.appendChild(olpages) body.appendChild(pageslist) navFile = open(str(Path(path / "nav.xhtml")), 'w', newline="", encoding="utf-8") navFile.write(navDoc.toString(indent=2)) navFile.close() return str(Path(path / "nav.xhtml"))
def write_opf_file(path, configDictionary, htmlFiles, pagesList, coverpageurl, coverpagehtml, listofSpreads): # marc relators # This has several entries removed to reduce it to the most relevant entries. marcRelators = { "abr": i18n("Abridger"), "acp": i18n("Art copyist"), "act": i18n("Actor"), "adi": i18n("Art director"), "adp": i18n("Adapter"), "ann": i18n("Annotator"), "ant": i18n("Bibliographic antecedent"), "arc": i18n("Architect"), "ard": i18n("Artistic director"), "art": i18n("Artist"), "asn": i18n("Associated name"), "ato": i18n("Autographer"), "att": i18n("Attributed name"), "aud": i18n("Author of dialog"), "aut": i18n("Author"), "bdd": i18n("Binding designer"), "bjd": i18n("Bookjacket designer"), "bkd": i18n("Book designer"), "bkp": i18n("Book producer"), "blw": i18n("Blurb writer"), "bnd": i18n("Binder"), "bpd": i18n("Bookplate designer"), "bsl": i18n("Bookseller"), "cll": i18n("Calligrapher"), "clr": i18n("Colorist"), "cns": i18n("Censor"), "cov": i18n("Cover designer"), "cph": i18n("Copyright holder"), "cre": i18n("Creator"), "ctb": i18n("Contributor"), "cur": i18n("Curator"), "cwt": i18n("Commentator for written text"), "drm": i18n("Draftsman"), "dsr": i18n("Designer"), "dub": i18n("Dubious author"), "edt": i18n("Editor"), "etr": i18n("Etcher"), "exp": i18n("Expert"), "fnd": i18n("Funder"), "ill": i18n("Illustrator"), "ilu": i18n("Illuminator"), "ins": i18n("Inscriber"), "lse": i18n("Licensee"), "lso": i18n("Licensor"), "ltg": i18n("Lithographer"), "mdc": i18n("Metadata contact"), "oth": i18n("Other"), "own": i18n("Owner"), "pat": i18n("Patron"), "pbd": i18n("Publishing director"), "pbl": i18n("Publisher"), "prt": i18n("Printer"), "sce": i18n("Scenarist"), "scr": i18n("Scribe"), "spn": i18n("Sponsor"), "stl": i18n("Storyteller"), "trc": i18n("Transcriber"), "trl": i18n("Translator"), "tyd": i18n("Type designer"), "tyg": i18n("Typographer"), "wac": i18n("Writer of added commentary"), "wal": i18n("Writer of added lyrics"), "wam": i18n("Writer of accompanying material"), "wat": i18n("Writer of added text"), "win": i18n("Writer of introduction"), "wpr": i18n("Writer of preface"), "wst": i18n("Writer of supplementary textual content") } # opf file opfFile = QDomDocument() opfRoot = opfFile.createElement("package") opfRoot.setAttribute("version", "3.0") opfRoot.setAttribute("unique-identifier", "BookId") opfRoot.setAttribute("xmlns", "http://www.idpf.org/2007/opf") opfRoot.setAttribute("prefix", "rendition: http://www.idpf.org/vocab/rendition/#") opfFile.appendChild(opfRoot) opfMeta = opfFile.createElement("metadata") opfMeta.setAttribute("xmlns:dc", "http://purl.org/dc/elements/1.1/") opfMeta.setAttribute("xmlns:dcterms", "http://purl.org/dc/terms/") # EPUB metadata requires a title, language and uuid langString = "en-US" if "language" in configDictionary.keys(): langString = str(configDictionary["language"]).replace("_", "-") bookLang = opfFile.createElement("dc:language") bookLang.appendChild(opfFile.createTextNode(langString)) opfMeta.appendChild(bookLang) bookTitle = opfFile.createElement("dc:title") if "title" in configDictionary.keys(): bookTitle.appendChild( opfFile.createTextNode(str(configDictionary["title"]))) else: bookTitle.appendChild(opfFile.createTextNode("Comic with no Name")) opfMeta.appendChild(bookTitle) # Generate series title and the like here too. if "seriesName" in configDictionary.keys(): bookTitle.setAttribute("id", "main") refine = opfFile.createElement("meta") refine.setAttribute("refines", "#main") refine.setAttribute("property", "title-type") refine.appendChild(opfFile.createTextNode("main")) opfMeta.appendChild(refine) refine2 = opfFile.createElement("meta") refine2.setAttribute("refines", "#main") refine2.setAttribute("property", "display-seq") refine2.appendChild(opfFile.createTextNode("1")) opfMeta.appendChild(refine2) seriesTitle = opfFile.createElement("dc:title") seriesTitle.appendChild( opfFile.createTextNode(str(configDictionary["seriesName"]))) seriesTitle.setAttribute("id", "series") opfMeta.appendChild(seriesTitle) refineS = opfFile.createElement("meta") refineS.setAttribute("refines", "#series") refineS.setAttribute("property", "title-type") refineS.appendChild(opfFile.createTextNode("collection")) opfMeta.appendChild(refineS) refineS2 = opfFile.createElement("meta") refineS2.setAttribute("refines", "#series") refineS2.setAttribute("property", "display-seq") refineS2.appendChild(opfFile.createTextNode("2")) opfMeta.appendChild(refineS2) if "seriesNumber" in configDictionary.keys(): refineS3 = opfFile.createElement("meta") refineS3.setAttribute("refines", "#series") refineS3.setAttribute("property", "group-position") refineS3.appendChild( opfFile.createTextNode(str(configDictionary["seriesNumber"]))) opfMeta.appendChild(refineS3) uuid = str(configDictionary["uuid"]) uuid = uuid.strip("{") uuid = uuid.strip("}") # Append the id, and assign it as the bookID. uniqueID = opfFile.createElement("dc:identifier") uniqueID.appendChild(opfFile.createTextNode("urn:uuid:" + uuid)) uniqueID.setAttribute("id", "BookId") opfMeta.appendChild(uniqueID) if "authorList" in configDictionary.keys(): authorEntry = 0 for authorE in range(len(configDictionary["authorList"])): authorDict = configDictionary["authorList"][authorE] authorType = "dc:creator" if "role" in authorDict.keys(): # This determines if someone was just a contributor, but might need a more thorough version. if str(authorDict["role"]).lower() in [ "editor", "assistant editor", "proofreader", "beta", "patron", "funder" ]: authorType = "dc:contributor" author = opfFile.createElement(authorType) authorName = [] if "last-name" in authorDict.keys(): authorName.append(authorDict["last-name"]) if "first-name" in authorDict.keys(): authorName.append(authorDict["first-name"]) if "initials" in authorDict.keys(): authorName.append(authorDict["initials"]) if "nickname" in authorDict.keys(): authorName.append("(" + authorDict["nickname"] + ")") author.appendChild(opfFile.createTextNode(", ".join(authorName))) author.setAttribute("id", "cre" + str(authorE)) opfMeta.appendChild(author) if "role" in authorDict.keys(): role = opfFile.createElement("meta") role.setAttribute("refines", "#cre" + str(authorE)) role.setAttribute("scheme", "marc:relators") role.setAttribute("property", "role") roleString = str(authorDict["role"]) if roleString in marcRelators.values( ) or roleString in marcRelators.keys(): i = list(marcRelators.values()).index(roleString) roleString = list(marcRelators.keys())[i] else: roleString = "oth" role.appendChild(opfFile.createTextNode(roleString)) opfMeta.appendChild(role) refine = opfFile.createElement("meta") refine.setAttribute("refines", "#cre" + str(authorE)) refine.setAttribute("property", "display-seq") refine.appendChild(opfFile.createTextNode(str(authorE + 1))) opfMeta.appendChild(refine) if "publishingDate" in configDictionary.keys(): date = opfFile.createElement("dc:date") date.appendChild( opfFile.createTextNode(configDictionary["publishingDate"])) opfMeta.appendChild(date) #Creation date modified = opfFile.createElement("meta") modified.setAttribute("property", "dcterms:modified") modified.appendChild( opfFile.createTextNode(QDateTime.currentDateTimeUtc().toString( Qt.ISODate))) opfMeta.appendChild(modified) if "source" in configDictionary.keys(): if len(configDictionary["source"]) > 0: source = opfFile.createElement("dc:source") source.appendChild( opfFile.createTextNode(configDictionary["source"])) opfMeta.appendChild(source) description = opfFile.createElement("dc:description") if "summary" in configDictionary.keys(): description.appendChild( opfFile.createTextNode(configDictionary["summary"])) else: description.appendChild( opfFile.createTextNode( "There was no summary upon generation of this file.")) opfMeta.appendChild(description) # Type can be dictionary or index, or one of those edupub thingies. Not necessary for comics. # typeE = opfFile.createElement("dc:type") # opfMeta.appendChild(typeE) if "publisherName" in configDictionary.keys(): publisher = opfFile.createElement("dc:publisher") publisher.appendChild( opfFile.createTextNode(configDictionary["publisherName"])) opfMeta.appendChild(publisher) if "isbn-number" in configDictionary.keys(): isbnnumber = configDictionary["isbn-number"] if len(isbnnumber) > 0: publishISBN = opfFile.createElement("dc:identifier") publishISBN.appendChild( opfFile.createTextNode(str("urn:isbn:") + isbnnumber)) opfMeta.appendChild(publishISBN) if "license" in configDictionary.keys(): if len(configDictionary["license"]) > 0: rights = opfFile.createElement("dc:rights") rights.appendChild( opfFile.createTextNode(configDictionary["license"])) opfMeta.appendChild(rights) """ Not handled Relation - This is for whether the work has a relationship with another work. It could be fanart, but also adaptation, an academic work, etc. Coverage - This is for the time/place that the work covers. Typically to determine whether an academic work deals with a certain time period or place. For comics you could use this to mark historical comics, but other than that we'd need a much better ui to define this. """ # These are all dublin core subjects. # 3.1 defines the ability to use an authority, but that # might be a bit too complicated right now. if "genre" in configDictionary.keys(): genreListConf = configDictionary["genre"] if isinstance(configDictionary["genre"], dict): genreListConf = configDictionary["genre"].keys() for g in genreListConf: subject = opfFile.createElement("dc:subject") subject.appendChild(opfFile.createTextNode(g)) opfMeta.appendChild(subject) if "characters" in configDictionary.keys(): for name in configDictionary["characters"]: char = opfFile.createElement("dc:subject") char.appendChild(opfFile.createTextNode(name)) opfMeta.appendChild(char) if "format" in configDictionary.keys(): for formatF in configDictionary["format"]: f = opfFile.createElement("dc:subject") f.appendChild(opfFile.createTextNode(formatF)) opfMeta.appendChild(f) if "otherKeywords" in configDictionary.keys(): for key in configDictionary["otherKeywords"]: word = opfFile.createElement("dc:subject") word.appendChild(opfFile.createTextNode(key)) opfMeta.appendChild(word) # Pre-pagination and layout # Comic are always prepaginated. elLayout = opfFile.createElement("meta") elLayout.setAttribute("property", "rendition:layout") elLayout.appendChild(opfFile.createTextNode("pre-paginated")) opfMeta.appendChild(elLayout) # We should figure out if the pages are portrait or not... elOrientation = opfFile.createElement("meta") elOrientation.setAttribute("property", "rendition:orientation") elOrientation.appendChild(opfFile.createTextNode("portrait")) opfMeta.appendChild(elOrientation) elSpread = opfFile.createElement("meta") elSpread.setAttribute("property", "rendition:spread") elSpread.appendChild(opfFile.createTextNode("landscape")) opfMeta.appendChild(elSpread) opfRoot.appendChild(opfMeta) # Manifest opfManifest = opfFile.createElement("manifest") toc = opfFile.createElement("item") toc.setAttribute("id", "ncx") toc.setAttribute("href", "toc.ncx") toc.setAttribute("media-type", "application/x-dtbncx+xml") opfManifest.appendChild(toc) region = opfFile.createElement("item") region.setAttribute("id", "regions") region.setAttribute("href", "region-nav.xhtml") region.setAttribute("media-type", "application/xhtml+xml") region.setAttribute("properties", "data-nav") # Set the propernavmap to use this later) opfManifest.appendChild(region) nav = opfFile.createElement("item") nav.setAttribute("id", "nav") nav.setAttribute("href", "nav.xhtml") nav.setAttribute("media-type", "application/xhtml+xml") nav.setAttribute("properties", "nav") # Set the propernavmap to use this later) opfManifest.appendChild(nav) ids = 0 for p in pagesList: item = opfFile.createElement("item") item.setAttribute("id", "img" + str(ids)) ids += 1 item.setAttribute("href", os.path.relpath(p, str(path))) item.setAttribute("media-type", "image/png") if os.path.basename(p) == os.path.basename(coverpageurl): item.setAttribute("properties", "cover-image") opfManifest.appendChild(item) ids = 0 for p in htmlFiles: item = opfFile.createElement("item") item.setAttribute("id", "p" + str(ids)) ids += 1 item.setAttribute("href", os.path.relpath(p, str(path))) item.setAttribute("media-type", "application/xhtml+xml") opfManifest.appendChild(item) opfRoot.appendChild(opfManifest) # Spine opfSpine = opfFile.createElement("spine") # this sets the table of contents to use the ncx file opfSpine.setAttribute("toc", "ncx") # Reading Direction: spreadRight = True direction = 0 if "readingDirection" in configDictionary.keys(): if configDictionary["readingDirection"] == "rightToLeft": opfSpine.setAttribute("page-progression-direction", "rtl") spreadRight = False direction = 1 else: opfSpine.setAttribute("page-progression-direction", "ltr") # Here we'd need to switch between the two and if spread keywrod use neither but combine with spread-none ids = 0 for p in htmlFiles: item = opfFile.createElement("itemref") item.setAttribute("idref", "p" + str(ids)) ids += 1 props = [] if p in listofSpreads: # Put this one in the center. props.append("rendition:page-spread-center") # Reset the spread boolean. # It needs to point at the first side after the spread. # So ltr -> spread-left, rtl->spread-right if direction == 0: spreadRight = False else: spreadRight = True else: if spreadRight: props.append("page-spread-right") spreadRight = False else: props.append("page-spread-left") spreadRight = True item.setAttribute("properties", " ".join(props)) opfSpine.appendChild(item) opfRoot.appendChild(opfSpine) # Guide opfGuide = opfFile.createElement("guide") if coverpagehtml is not None and coverpagehtml.isspace() is False and len( coverpagehtml) > 0: item = opfFile.createElement("reference") item.setAttribute("type", "cover") item.setAttribute("title", "Cover") item.setAttribute("href", coverpagehtml) opfGuide.appendChild(item) opfRoot.appendChild(opfGuide) docFile = open(str(Path(path / "content.opf")), 'w', newline="", encoding="utf-8") docFile.write(opfFile.toString(indent=2)) docFile.close() return str(Path(path / "content.opf"))
class GrapholExporter(AbstractExporter): """ This class can be used to export Graphol diagrams to file. """ def __init__(self, scene): """ Initialize the Graphol exporter. :type scene: DiagramScene """ super().__init__(scene) self.document = None self.itemToXml = { Item.AttributeNode: 'attribute', Item.ComplementNode: 'complement', Item.ConceptNode: 'concept', Item.DatatypeRestrictionNode: 'datatype-restriction', Item.DisjointUnionNode: 'disjoint-union', Item.DomainRestrictionNode: 'domain-restriction', Item.EnumerationNode: 'enumeration', Item.IndividualNode: 'individual', Item.IntersectionNode: 'intersection', Item.PropertyAssertionNode: 'property-assertion', Item.RangeRestrictionNode: 'range-restriction', Item.RoleNode: 'role', Item.RoleChainNode: 'role-chain', Item.RoleInverseNode: 'role-inverse', Item.UnionNode: 'union', Item.ValueDomainNode: 'value-domain', Item.ValueRestrictionNode: 'value-restriction', Item.InclusionEdge: 'inclusion', Item.InputEdge: 'input', Item.InstanceOfEdge: 'instance-of', } #################################################################################################################### # # # NODES # # # #################################################################################################################### def exportAttributeNode(self, node): """ Export the given node into a QDomElement. :type node: AttributeNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportComplementNode(self, node): """ Export the given node into a QDomElement. :type node: ComplementNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportConceptNode(self, node): """ Export the given node into a QDomElement. :type node: ConceptNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportDatatypeRestrictionNode(self, node): """ Export the given node into a QDomElement. :type node: DatatypeRestrictionNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportDisjointUnionNode(self, node): """ Export the given node into a QDomElement. :type node: DisjointUnionNode :rtype: QDomElement """ return self.exportGenericNode(node) def exportDomainRestrictionNode(self, node): """ Export the given node into a QDomElement. :type node: DomainRestrictionNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportEnumerationNode(self, node): """ Export the given node into a QDomElement. :type node: EnumerationNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportIndividualNode(self, node): """ Export the given node into a QDomElement. :type node: IndividualNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportIntersectionNode(self, node): """ Export the given node into a QDomElement. :type node: IntersectionNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportPropertyAssertionNode(self, node): """ Export the given node into a QDomElement. :type node: PropertyAssertionNode :rtype: QDomElement """ element = self.exportGenericNode(node) element.setAttribute('inputs', ','.join(node.inputs)) return element def exportRangeRestrictionNode(self, node): """ Export the given node into a QDomElement. :type node: RangeRestrictionNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportRoleNode(self, node): """ Export the given node into a QDomElement. :type node: RoleNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportRoleChainNode(self, node): """ Export the given node into a QDomElement. :type node: RoleChainNode :rtype: QDomElement """ element = self.exportLabelNode(node) element.setAttribute('inputs', ','.join(node.inputs)) return element def exportRoleInverseNode(self, node): """ Export the given node into a QDomElement. :type node: RoleInverseNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportValueDomainNode(self, node): """ Export the given node into a QDomElement. :type node: ValueDomainNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportUnionNode(self, node): """ Export the given node into a QDomElement. :type node: UnionNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportValueRestrictionNode(self, node): """ Export the given node into a QDomElement. :type node: ValueRestrictionNode :rtype: QDomElement """ return self.exportLabelNode(node) #################################################################################################################### # # # EDGES # # # #################################################################################################################### def exportInclusionEdge(self, edge): """ Export the given edge into a QDomElement. :type edge: InclusionEdge :rtype: QDomElement """ element = self.exportGenericEdge(edge) element.setAttribute('complete', int(edge.complete)) return element def exportInputEdge(self, edge): """ Export the given edge into a QDomElement. :type edge: InputEdge :rtype: QDomElement """ return self.exportGenericEdge(edge) def exportInstanceOfEdge(self, edge): """ Export the given edge into a QDomElement. :type edge: InstanceOf :rtype: QDomElement """ return self.exportGenericEdge(edge) #################################################################################################################### # # # METADATA # # # #################################################################################################################### def exportPredicateMetadata(self, item, predicate): """ Export given predicate metadata. :type item: Item :type predicate: str :rtype: QDomElement """ meta = self.scene.meta.metaFor(item, predicate) if meta: element = self.document.createElement('meta') element.setAttribute('type', self.itemToXml[item]) element.setAttribute('predicate', predicate) url = self.document.createElement('data:url') url.appendChild(self.document.createTextNode(meta.url)) description = self.document.createElement('data:description') description.appendChild( self.document.createTextNode(meta.description)) element.appendChild(url) element.appendChild(description) return element return None def exportAttributeMetadata(self, item, predicate): """ Export given attribute metadata. :type item: Item :type predicate: str :rtype: QDomElement """ element = self.exportPredicateMetadata(item, predicate) if element: meta = self.scene.meta.metaFor(item, predicate) if meta: functionality = self.document.createElement( 'data:functionality') functionality.appendChild( self.document.createTextNode(str(int(meta.functionality)))) element.appendChild(functionality) return element return None def exportRoleMetadata(self, item, predicate): """ Export given role metadata :type item: Item :type predicate: str :rtype: QDomElement """ element = self.exportPredicateMetadata(item, predicate) if element: meta = self.scene.meta.metaFor(item, predicate) if meta: functionality = self.document.createElement( 'data:functionality') functionality.appendChild( self.document.createTextNode(str(int(meta.functionality)))) inverseFunctionality = self.document.createElement( 'data:inverseFunctionality') inverseFunctionality.appendChild( self.document.createTextNode( str(int(meta.inverseFunctionality)))) asymmetry = self.document.createElement('data:asymmetry') asymmetry.appendChild( self.document.createTextNode(str(int(meta.asymmetry)))) irreflexivity = self.document.createElement( 'data:irreflexivity') irreflexivity.appendChild( self.document.createTextNode(str(int(meta.irreflexivity)))) reflexivity = self.document.createElement('data:reflexivity') reflexivity.appendChild( self.document.createTextNode(str(int(meta.reflexivity)))) symmetry = self.document.createElement('data:symmetry') symmetry.appendChild( self.document.createTextNode(str(int(meta.symmetry)))) transitivity = self.document.createElement('data:transitivity') transitivity.appendChild( self.document.createTextNode(str(int(meta.transitivity)))) element.appendChild(functionality) element.appendChild(inverseFunctionality) element.appendChild(asymmetry) element.appendChild(irreflexivity) element.appendChild(reflexivity) element.appendChild(symmetry) element.appendChild(transitivity) return element return None #################################################################################################################### # # # AUXILIARY METHODS # # # #################################################################################################################### def exportLabelNode(self, node): """ Export the given node into a QDomElement. :type node: AbstractNode :rtype: QDomElement """ position = node.mapToScene(node.textPos()) label = self.document.createElement('shape:label') label.setAttribute('height', node.label.height()) label.setAttribute('width', node.label.width()) label.setAttribute('x', position.x()) label.setAttribute('y', position.y()) label.appendChild(self.document.createTextNode(node.text())) element = self.exportGenericNode(node) element.appendChild(label) return element def exportGenericEdge(self, edge): """ Export the given node into a QDomElement. :type edge: AbstractEdge :rtype: QDomElement """ element = self.document.createElement('edge') element.setAttribute('source', edge.source.id) element.setAttribute('target', edge.target.id) element.setAttribute('id', edge.id) element.setAttribute('type', self.itemToXml[edge.item]) for p in [edge.source.anchor(edge) ] + edge.breakpoints + [edge.target.anchor(edge)]: point = self.document.createElement('line:point') point.setAttribute('x', p.x()) point.setAttribute('y', p.y()) element.appendChild(point) return element def exportGenericNode(self, node): """ Export the given node into a QDomElement. :type node: AbstractNode :rtype: QDomElement """ element = self.document.createElement('node') element.setAttribute('id', node.id) element.setAttribute('type', self.itemToXml[node.item]) element.setAttribute('color', node.brush.color().name()) geometry = self.document.createElement('shape:geometry') geometry.setAttribute('height', node.height()) geometry.setAttribute('width', node.width()) geometry.setAttribute('x', node.pos().x()) geometry.setAttribute('y', node.pos().y()) element.appendChild(geometry) return element #################################################################################################################### # # # DOCUMENT EXPORT # # # #################################################################################################################### def export(self, indent=4): """ Export the coverted ontology. :type indent: int :rtype: str """ return self.document.toString(indent) #################################################################################################################### # # # DOCUMENT GENERATION # # # #################################################################################################################### def run(self): """ Perform Graphol ontology generation. """ # 1) CREATE THE DOCUMENT self.document = QDomDocument() self.document.appendChild( self.document.createProcessingInstruction( 'xml', 'version="1.0" ' 'encoding="UTF-8" ' 'standalone="no"')) # 2) CREATE ROOT ELEMENT root = self.document.createElement('graphol') root.setAttribute('xmlns', 'http://www.dis.uniroma1.it/~graphol/schema') root.setAttribute('xmlns:xsi', 'http://www.w3.org/2001/XMLSchema-instance') root.setAttribute('xmlns:data', 'http://www.dis.uniroma1.it/~graphol/schema/data') root.setAttribute('xmlns:line', 'http://www.dis.uniroma1.it/~graphol/schema/line') root.setAttribute('xmlns:shape', 'http://www.dis.uniroma1.it/~graphol/schema/shape') root.setAttribute( 'xsi:schemaLocation', 'http://www.dis.uniroma1.it/~graphol/schema ' 'http://www.dis.uniroma1.it/~graphol/schema/graphol.xsd') self.document.appendChild(root) # 3) CREATE THE GRAPH NODE graph = self.document.createElement('graph') graph.setAttribute('width', self.scene.sceneRect().width()) graph.setAttribute('height', self.scene.sceneRect().height()) # 4) GENERATE NODES for node in self.scene.nodes(): element = None if node.item is Item.AttributeNode: element = self.exportAttributeNode(node) elif node.item is Item.ComplementNode: element = self.exportComplementNode(node) elif node.item is Item.ConceptNode: element = self.exportConceptNode(node) elif node.item is Item.DatatypeRestrictionNode: element = self.exportDatatypeRestrictionNode(node) elif node.item is Item.DisjointUnionNode: element = self.exportDisjointUnionNode(node) elif node.item is Item.DomainRestrictionNode: element = self.exportDomainRestrictionNode(node) elif node.item is Item.EnumerationNode: element = self.exportEnumerationNode(node) elif node.item is Item.IndividualNode: element = self.exportIndividualNode(node) elif node.item is Item.IntersectionNode: element = self.exportIntersectionNode(node) elif node.item is Item.PropertyAssertionNode: element = self.exportPropertyAssertionNode(node) elif node.item is Item.RangeRestrictionNode: element = self.exportRangeRestrictionNode(node) elif node.item is Item.RoleNode: element = self.exportRoleNode(node) elif node.item is Item.RoleChainNode: element = self.exportRoleChainNode(node) elif node.item is Item.RoleInverseNode: element = self.exportRoleInverseNode(node) elif node.item is Item.UnionNode: element = self.exportUnionNode(node) elif node.item is Item.ValueDomainNode: element = self.exportValueDomainNode(node) elif node.item is Item.ValueRestrictionNode: element = self.exportValueRestrictionNode(node) if not element: raise ValueError('unknown node: {}'.format(node)) graph.appendChild(element) # 5) GENERATE EDGES for edge in self.scene.edges(): element = None if edge.item is Item.InclusionEdge: element = self.exportInclusionEdge(edge) elif edge.item is Item.InputEdge: element = self.exportInputEdge(edge) elif edge.item is Item.InstanceOfEdge: element = self.exportInstanceOfEdge(edge) if not element: raise ValueError('unknown edge: {}'.format(edge)) graph.appendChild(element) # 6) APPEND THE GRAPH TO THE DOCUMENT root.appendChild(graph) # 7) GENERATE NODES META DATA collection = [] for item, predicate in self.scene.meta.entries(): if item is Item.RoleNode: element = self.exportRoleMetadata(item, predicate) elif item is Item.AttributeNode: element = self.exportAttributeMetadata(item, predicate) else: element = self.exportPredicateMetadata(item, predicate) if element: collection.append(element) if collection: metadata = self.document.createElement('metadata') for element in collection: metadata.appendChild(element) root.appendChild(metadata)
class GrapholExporter(AbstractExporter): """ This class can be used to export Graphol diagrams to file. """ def __init__(self, scene): """ Initialize the Graphol exporter. :type scene: DiagramScene """ super().__init__(scene) self.document = None self.itemToXml = { Item.AttributeNode: 'attribute', Item.ComplementNode: 'complement', Item.ConceptNode: 'concept', Item.DatatypeRestrictionNode: 'datatype-restriction', Item.DisjointUnionNode: 'disjoint-union', Item.DomainRestrictionNode: 'domain-restriction', Item.EnumerationNode: 'enumeration', Item.IndividualNode: 'individual', Item.IntersectionNode: 'intersection', Item.PropertyAssertionNode: 'property-assertion', Item.RangeRestrictionNode: 'range-restriction', Item.RoleNode: 'role', Item.RoleChainNode: 'role-chain', Item.RoleInverseNode: 'role-inverse', Item.UnionNode: 'union', Item.ValueDomainNode: 'value-domain', Item.ValueRestrictionNode: 'value-restriction', Item.InclusionEdge: 'inclusion', Item.InputEdge: 'input', Item.InstanceOfEdge: 'instance-of', } #################################################################################################################### # # # NODES # # # #################################################################################################################### def exportAttributeNode(self, node): """ Export the given node into a QDomElement. :type node: AttributeNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportComplementNode(self, node): """ Export the given node into a QDomElement. :type node: ComplementNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportConceptNode(self, node): """ Export the given node into a QDomElement. :type node: ConceptNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportDatatypeRestrictionNode(self, node): """ Export the given node into a QDomElement. :type node: DatatypeRestrictionNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportDisjointUnionNode(self, node): """ Export the given node into a QDomElement. :type node: DisjointUnionNode :rtype: QDomElement """ return self.exportGenericNode(node) def exportDomainRestrictionNode(self, node): """ Export the given node into a QDomElement. :type node: DomainRestrictionNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportEnumerationNode(self, node): """ Export the given node into a QDomElement. :type node: EnumerationNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportIndividualNode(self, node): """ Export the given node into a QDomElement. :type node: IndividualNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportIntersectionNode(self, node): """ Export the given node into a QDomElement. :type node: IntersectionNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportPropertyAssertionNode(self, node): """ Export the given node into a QDomElement. :type node: PropertyAssertionNode :rtype: QDomElement """ element = self.exportGenericNode(node) element.setAttribute('inputs', ','.join(node.inputs)) return element def exportRangeRestrictionNode(self, node): """ Export the given node into a QDomElement. :type node: RangeRestrictionNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportRoleNode(self, node): """ Export the given node into a QDomElement. :type node: RoleNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportRoleChainNode(self, node): """ Export the given node into a QDomElement. :type node: RoleChainNode :rtype: QDomElement """ element = self.exportLabelNode(node) element.setAttribute('inputs', ','.join(node.inputs)) return element def exportRoleInverseNode(self, node): """ Export the given node into a QDomElement. :type node: RoleInverseNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportValueDomainNode(self, node): """ Export the given node into a QDomElement. :type node: ValueDomainNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportUnionNode(self, node): """ Export the given node into a QDomElement. :type node: UnionNode :rtype: QDomElement """ return self.exportLabelNode(node) def exportValueRestrictionNode(self, node): """ Export the given node into a QDomElement. :type node: ValueRestrictionNode :rtype: QDomElement """ return self.exportLabelNode(node) #################################################################################################################### # # # EDGES # # # #################################################################################################################### def exportInclusionEdge(self, edge): """ Export the given edge into a QDomElement. :type edge: InclusionEdge :rtype: QDomElement """ element = self.exportGenericEdge(edge) element.setAttribute('complete', int(edge.complete)) return element def exportInputEdge(self, edge): """ Export the given edge into a QDomElement. :type edge: InputEdge :rtype: QDomElement """ return self.exportGenericEdge(edge) def exportInstanceOfEdge(self, edge): """ Export the given edge into a QDomElement. :type edge: InstanceOf :rtype: QDomElement """ return self.exportGenericEdge(edge) #################################################################################################################### # # # METADATA # # # #################################################################################################################### def exportPredicateMetadata(self, item, predicate): """ Export given predicate metadata. :type item: Item :type predicate: str :rtype: QDomElement """ meta = self.scene.meta.metaFor(item, predicate) if meta: element = self.document.createElement('meta') element.setAttribute('type', self.itemToXml[item]) element.setAttribute('predicate', predicate) url = self.document.createElement('data:url') url.appendChild(self.document.createTextNode(meta.url)) description = self.document.createElement('data:description') description.appendChild(self.document.createTextNode(meta.description)) element.appendChild(url) element.appendChild(description) return element return None def exportAttributeMetadata(self, item, predicate): """ Export given attribute metadata. :type item: Item :type predicate: str :rtype: QDomElement """ element = self.exportPredicateMetadata(item, predicate) if element: meta = self.scene.meta.metaFor(item, predicate) if meta: functionality = self.document.createElement('data:functionality') functionality.appendChild(self.document.createTextNode(str(int(meta.functionality)))) element.appendChild(functionality) return element return None def exportRoleMetadata(self, item, predicate): """ Export given role metadata :type item: Item :type predicate: str :rtype: QDomElement """ element = self.exportPredicateMetadata(item, predicate) if element: meta = self.scene.meta.metaFor(item, predicate) if meta: functionality = self.document.createElement('data:functionality') functionality.appendChild(self.document.createTextNode(str(int(meta.functionality)))) inverseFunctionality = self.document.createElement('data:inverseFunctionality') inverseFunctionality.appendChild(self.document.createTextNode(str(int(meta.inverseFunctionality)))) asymmetry = self.document.createElement('data:asymmetry') asymmetry.appendChild(self.document.createTextNode(str(int(meta.asymmetry)))) irreflexivity = self.document.createElement('data:irreflexivity') irreflexivity.appendChild(self.document.createTextNode(str(int(meta.irreflexivity)))) reflexivity = self.document.createElement('data:reflexivity') reflexivity.appendChild(self.document.createTextNode(str(int(meta.reflexivity)))) symmetry = self.document.createElement('data:symmetry') symmetry.appendChild(self.document.createTextNode(str(int(meta.symmetry)))) transitivity = self.document.createElement('data:transitivity') transitivity.appendChild(self.document.createTextNode(str(int(meta.transitivity)))) element.appendChild(functionality) element.appendChild(inverseFunctionality) element.appendChild(asymmetry) element.appendChild(irreflexivity) element.appendChild(reflexivity) element.appendChild(symmetry) element.appendChild(transitivity) return element return None #################################################################################################################### # # # AUXILIARY METHODS # # # #################################################################################################################### def exportLabelNode(self, node): """ Export the given node into a QDomElement. :type node: AbstractNode :rtype: QDomElement """ position = node.mapToScene(node.textPos()) label = self.document.createElement('shape:label') label.setAttribute('height', node.label.height()) label.setAttribute('width', node.label.width()) label.setAttribute('x', position.x()) label.setAttribute('y', position.y()) label.appendChild(self.document.createTextNode(node.text())) element = self.exportGenericNode(node) element.appendChild(label) return element def exportGenericEdge(self, edge): """ Export the given node into a QDomElement. :type edge: AbstractEdge :rtype: QDomElement """ element = self.document.createElement('edge') element.setAttribute('source', edge.source.id) element.setAttribute('target', edge.target.id) element.setAttribute('id', edge.id) element.setAttribute('type', self.itemToXml[edge.item]) for p in [edge.source.anchor(edge)] + edge.breakpoints + [edge.target.anchor(edge)]: point = self.document.createElement('line:point') point.setAttribute('x', p.x()) point.setAttribute('y', p.y()) element.appendChild(point) return element def exportGenericNode(self, node): """ Export the given node into a QDomElement. :type node: AbstractNode :rtype: QDomElement """ element = self.document.createElement('node') element.setAttribute('id', node.id) element.setAttribute('type', self.itemToXml[node.item]) element.setAttribute('color', node.brush.color().name()) geometry = self.document.createElement('shape:geometry') geometry.setAttribute('height', node.height()) geometry.setAttribute('width', node.width()) geometry.setAttribute('x', node.pos().x()) geometry.setAttribute('y', node.pos().y()) element.appendChild(geometry) return element #################################################################################################################### # # # DOCUMENT EXPORT # # # #################################################################################################################### def export(self, indent=4): """ Export the coverted ontology. :type indent: int :rtype: str """ return self.document.toString(indent) #################################################################################################################### # # # DOCUMENT GENERATION # # # #################################################################################################################### def run(self): """ Perform Graphol ontology generation. """ # 1) CREATE THE DOCUMENT self.document = QDomDocument() self.document.appendChild(self.document.createProcessingInstruction('xml', 'version="1.0" ' 'encoding="UTF-8" ' 'standalone="no"')) # 2) CREATE ROOT ELEMENT root = self.document.createElement('graphol') root.setAttribute('xmlns', 'http://www.dis.uniroma1.it/~graphol/schema') root.setAttribute('xmlns:xsi', 'http://www.w3.org/2001/XMLSchema-instance') root.setAttribute('xmlns:data', 'http://www.dis.uniroma1.it/~graphol/schema/data') root.setAttribute('xmlns:line', 'http://www.dis.uniroma1.it/~graphol/schema/line') root.setAttribute('xmlns:shape', 'http://www.dis.uniroma1.it/~graphol/schema/shape') root.setAttribute('xsi:schemaLocation', 'http://www.dis.uniroma1.it/~graphol/schema ' 'http://www.dis.uniroma1.it/~graphol/schema/graphol.xsd') self.document.appendChild(root) # 3) CREATE THE GRAPH NODE graph = self.document.createElement('graph') graph.setAttribute('width', self.scene.sceneRect().width()) graph.setAttribute('height', self.scene.sceneRect().height()) # 4) GENERATE NODES for node in self.scene.nodes(): element = None if node.item is Item.AttributeNode: element = self.exportAttributeNode(node) elif node.item is Item.ComplementNode: element = self.exportComplementNode(node) elif node.item is Item.ConceptNode: element = self.exportConceptNode(node) elif node.item is Item.DatatypeRestrictionNode: element = self.exportDatatypeRestrictionNode(node) elif node.item is Item.DisjointUnionNode: element = self.exportDisjointUnionNode(node) elif node.item is Item.DomainRestrictionNode: element = self.exportDomainRestrictionNode(node) elif node.item is Item.EnumerationNode: element = self.exportEnumerationNode(node) elif node.item is Item.IndividualNode: element = self.exportIndividualNode(node) elif node.item is Item.IntersectionNode: element = self.exportIntersectionNode(node) elif node.item is Item.PropertyAssertionNode: element = self.exportPropertyAssertionNode(node) elif node.item is Item.RangeRestrictionNode: element = self.exportRangeRestrictionNode(node) elif node.item is Item.RoleNode: element = self.exportRoleNode(node) elif node.item is Item.RoleChainNode: element = self.exportRoleChainNode(node) elif node.item is Item.RoleInverseNode: element = self.exportRoleInverseNode(node) elif node.item is Item.UnionNode: element = self.exportUnionNode(node) elif node.item is Item.ValueDomainNode: element = self.exportValueDomainNode(node) elif node.item is Item.ValueRestrictionNode: element = self.exportValueRestrictionNode(node) if not element: raise ValueError('unknown node: {}'.format(node)) graph.appendChild(element) # 5) GENERATE EDGES for edge in self.scene.edges(): element = None if edge.item is Item.InclusionEdge: element = self.exportInclusionEdge(edge) elif edge.item is Item.InputEdge: element = self.exportInputEdge(edge) elif edge.item is Item.InstanceOfEdge: element = self.exportInstanceOfEdge(edge) if not element: raise ValueError('unknown edge: {}'.format(edge)) graph.appendChild(element) # 6) APPEND THE GRAPH TO THE DOCUMENT root.appendChild(graph) # 7) GENERATE NODES META DATA collection = [] for item, predicate in self.scene.meta.entries(): if item is Item.RoleNode: element = self.exportRoleMetadata(item, predicate) elif item is Item.AttributeNode: element = self.exportAttributeMetadata(item, predicate) else: element = self.exportPredicateMetadata(item, predicate) if element: collection.append(element) if collection: metadata = self.document.createElement('metadata') for element in collection: metadata.appendChild(element) root.appendChild(metadata)
def qml2Sld(self): try: layer = self.allMapLayers[self.dlg.comboBox.currentIndex()] except: return qmlDocument = QDomDocument() root = qmlDocument.createElement('SLD4raster') qmlDocument.appendChild(root) qgisNode = qmlDocument.createElement('qgis') root.appendChild(qgisNode) errorMessage = None context = QgsReadWriteContext() layer.writeSymbology(qgisNode, qmlDocument, errorMessage, context) qmlString = minidom.parseString(qmlDocument.toString().encode('utf-8')) # for non ASCII labels. sldRoot = Element('sld:StyledLayerDescriptor') sldRoot.attrib['xmlns'] = 'http://www.opengis.net/sld' sldRoot.attrib['xmlns:sld'] = 'http://www.opengis.net/sld' sldRoot.attrib['xmlns:ogc'] = 'http://www.opengis.net/ogc' sldRoot.attrib['xmlns:gml'] = 'http://www.opengis.net/gml' sldRoot.attrib['version'] = '1.0.0' userLayer = SubElement(sldRoot, 'sld:UserLayer') layerFeatureConstraints = SubElement(userLayer, 'sld:LayerFeatureConstraints') featureTypeConstraint = SubElement(layerFeatureConstraints, 'sld:FeatureTypeConstraint') userStyle = SubElement(userLayer, 'sld:UserStyle') styleName = SubElement(userStyle, 'sld:Name') styleName.text = self.dlg.comboBox.currentText() styleDescription = SubElement(userStyle, 'sld:Description') styleDescription.text = 'Generated by SLD4raster - https://cbsuygulama.wordpress.com/sld4raster' styleTitle = SubElement(userStyle, 'sld:Title') featureTypeStyle = SubElement(userStyle, 'sld:FeatureTypeStyle') featureName = SubElement(featureTypeStyle, 'sld:Name') featureRule = SubElement(featureTypeStyle, 'sld:Rule') rasterSymbolizer = SubElement(featureRule, 'sld:RasterSymbolizer') geometry = SubElement(rasterSymbolizer, 'sld:Geometry') ogcPropertyName = SubElement(geometry, 'ogc:PropertyName') ogcPropertyName.text = 'grid' opacity = SubElement(rasterSymbolizer, 'sld:Opacity') ###Getting raster type parameters rasterType = str(qmlString.getElementsByTagName('rasterrenderer')[0].attributes['type'].value) isGradient = 'gradient' in qmlString.getElementsByTagName('rasterrenderer')[0].attributes.keys() ###SLD for multiband raster if rasterType == 'multibandcolor': ###Getting RGB band order. redBand = str(qmlString.getElementsByTagName('rasterrenderer')[0].attributes['redBand'].value) greenBand = str(qmlString.getElementsByTagName('rasterrenderer')[0].attributes['greenBand'].value) blueBand = str(qmlString.getElementsByTagName('rasterrenderer')[0].attributes['blueBand'].value) channelSelection = SubElement(rasterSymbolizer, 'sld:ChannelSelection') redChannel = SubElement(channelSelection, 'sld:RedChannel') redSourceChannel = SubElement(redChannel, 'sld:SourceChannelName') redSourceChannel.text = redBand greenChannel = SubElement(channelSelection, 'sld:GreenChannel') greenSourceChannel = SubElement(greenChannel, 'sld:SourceChannelName') greenSourceChannel.text = greenBand blueChannel = SubElement(channelSelection, 'sld:BlueChannel') blueSourceChannel = SubElement(blueChannel, 'sld:SourceChannelName') blueSourceChannel.text = blueBand ###SLD for gradiented (black to white) raster elif isGradient: blackWhiteColor = ['#000000', '#FFFFFF'] colorMap = SubElement(rasterSymbolizer, 'sld:ColorMap') gradientType = qmlString.getElementsByTagName('rasterrenderer')[0].attributes['gradient'].value blackWhiteValue = [qmlString.getElementsByTagName('minValue')[0].firstChild.nodeValue, qmlString.getElementsByTagName('maxValue')[0].firstChild.nodeValue] ###Getting gradient color type if gradientType == 'WhiteToBlack': blackWhiteColor.reverse() for i in range(len(blackWhiteColor)): colorMapEntry = SubElement(colorMap, 'sld:ColorMapEntry') colorMapEntry.attrib['color'] = blackWhiteColor[i] colorMapEntry.attrib['opacity'] = '1.0' colorMapEntry.attrib['quantity'] = blackWhiteValue[i] ###SLD for singleband raster else: colorMap = SubElement(rasterSymbolizer, 'sld:ColorMap') ###Getting color ramp type colorType = str(qmlString.getElementsByTagName('colorrampshader')[0].attributes['colorRampType'].value) if colorType == 'DISCRETE': colorMap.attrib['type'] = "intervals" ###Getting color values colorValue = list() itemlist = qmlString.getElementsByTagName('item') for n in itemlist: colorValue.append( [n.attributes['color'].value, n.attributes['value'].value, n.attributes['label'].value]) ###Color values posting to SLD document for i in range(len(colorValue)): colorMapEntry = SubElement(colorMap, 'sld:ColorMapEntry') colorMapEntry.attrib['color'] = colorValue[i][0] colorMapEntry.attrib['quantity'] = colorValue[i][1] colorMapEntry.attrib['label'] = colorValue[i][2] colorMapEntry.attrib['opacity'] = '1.0' rasterOpacity = str(qmlString.getElementsByTagName('rasterrenderer')[0].attributes['opacity'].value) opacity.text = rasterOpacity textSLD = minidom.parseString(tostring(sldRoot)) self.dlg.sldText1.setText(textSLD.toprettyxml(indent=" "))
class MultiDaemonFile: file_path = '/tmp/RaySession/multi-daemon.xml' def __init__(self, session, server): self.session = session self.server = server self._xml = QDomDocument() global instance instance = self self._locked_session_paths = set() @staticmethod def get_instance(): return instance def _pid_exists(self, pid)->bool: if isinstance(pid, str): pid = int(pid) try: os.kill(pid, 0) except OSError: return False else: return True def _remove_file(self): try: os.remove(self.file_path) except: return def _open_file(self)->bool: if not os.path.exists(self.file_path): dir_path = os.path.dirname(self.file_path) if not os.path.exists(dir_path): os.makedirs(dir_path) # give read/write access for all users os.chmod(dir_path, 0o777) return False try: file = open(self.file_path, 'r') self._xml.setContent(file.read()) file.close() return True except: self._remove_file() return False def _write_file(self): try: file = open(self.file_path, 'w') file.write(self._xml.toString()) file.close() except: return def _set_attributes(self, element): element.setAttribute('net_daemon_id', self.server.net_daemon_id) element.setAttribute('root', self.session.root) element.setAttribute('session_path', self.session.path) element.setAttribute('pid', os.getpid()) element.setAttribute('port', self.server.port) element.setAttribute('user', os.getenv('USER')) element.setAttribute('not_default', int(bool(self.server.is_nsm_locked or self.server.not_default))) element.setAttribute('has_gui', int(self.server.has_gui())) element.setAttribute('version', ray.VERSION) element.setAttribute('local_gui_pids', self.server.get_local_gui_pid_list()) for locked_path in self._locked_session_paths: locked_paths_xml = self._xml.createElement('locked_session') locked_paths_xml.setAttribute('path', locked_path) element.appendChild(locked_paths_xml) def _clean_dirty_pids(self): xml_content = self._xml.documentElement() nodes = xml_content.childNodes() rm_nodes = [] for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() pid = dxe.attribute('pid') if not pid.isdigit() or not self._pid_exists(int(pid)): rm_nodes.append(node) for node in rm_nodes: xml_content.removeChild(node) def update(self): has_dirty_pid = False if not self._open_file(): ds = self._xml.createElement('Daemons') dm_xml = self._xml.createElement('Daemon') self._set_attributes(dm_xml) ds.appendChild(dm_xml) self._xml.appendChild(ds) else: xml_content = self._xml.documentElement() nodes = xml_content.childNodes() self_node = None for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() pid = dxe.attribute('pid') if pid.isdigit() and pid == str(os.getpid()): self_node = node elif not pid.isdigit() or not self._pid_exists(int(pid)): has_dirty_pid = True if self_node is not None: xml_content.removeChild(self_node) dm_xml = self._xml.createElement('Daemon') self._set_attributes(dm_xml) self._xml.firstChild().appendChild(dm_xml) if has_dirty_pid: self._clean_dirty_pids() self._write_file() def quit(self): if not self._open_file(): return xml_content = self._xml.documentElement() nodes = xml_content.childNodes() for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() pid = dxe.attribute('pid') if pid.isdigit() and pid == str(os.getpid()): break else: return xml_content.removeChild(node) self._write_file() def is_free_for_root(self, daemon_id, root_path)->bool: if not self._open_file(): return True xml_content = self._xml.documentElement() nodes = xml_content.childNodes() for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() if (dxe.attribute('net_daemon_id') == str(daemon_id) and dxe.attribute('root') == root_path): pid = dxe.attribute('pid') if pid.isdigit() and self._pid_exists(int(pid)): return False return True def is_free_for_session(self, session_path)->bool: if not self._open_file(): return True xml_content = self._xml.documentElement() nodes = xml_content.childNodes() for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() pid = dxe.attribute('pid') if dxe.attribute('session_path') == session_path: if pid.isdigit() and self._pid_exists(int(pid)): return False sub_nodes = node.childNodes() for j in range(sub_nodes.count()): sub_node = sub_nodes.at(j) sub_nod_el = sub_node.toElement() if sub_nod_el.attribute('path') == session_path: if pid.isdigit() and self._pid_exists(int(pid)): return False return True def get_all_session_paths(self)->list: if not self._open_file(): return [] all_session_paths = [] xml_content = self._xml.documentElement() nodes = xml_content.childNodes() for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() spath = dxe.attribute('session_path') pid = dxe.attribute('pid') if spath and pid.isdigit() and self._pid_exists(int(pid)): all_session_paths.append(spath) return all_session_paths def add_locked_path(self, path:str): self._locked_session_paths.add(path) self.update() def unlock_path(self, path:str): self._locked_session_paths.discard(path) self.update() def get_daemon_list(self)->list: daemon_list = [] has_dirty_pid = False if not self._open_file(): return daemon_list xml_content = self._xml.documentElement() nodes = xml_content.childNodes() for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() daemon = Daemon() daemon.root = dxe.attribute('root') daemon.session_path = dxe.attribute('session_path') daemon.user = dxe.attribute('user') daemon.not_default = bool(dxe.attribute('not_default') == 'true') net_daemon_id = dxe.attribute('net_daemon_id') pid = dxe.attribute('pid') port = dxe.attribute('port') if net_daemon_id.isdigit(): daemon.net_daemon_id = net_daemon_id if pid.isdigit(): daemon.pid = pid if port.isdigit(): daemon.port = port if not self._pid_exists(daemon.pid): has_dirty_pid = True continue if not (daemon.net_daemon_id and daemon.pid and daemon.port): continue daemon_list.append(daemon) if has_dirty_pid: self._clean_dirty_pids() return daemon_list
def export(self): # open the appropriate file... svgFile = open(self.fileName + "/" + self.paletteName + ".svg", "w") svgDoc = QDomDocument() svgBaseElement = svgDoc.createElement("svg") svgBaseElement.setAttribute( "xmlns:osb", "http://www.openswatchbook.org/uri/2009/osb") svgBaseElement.setAttribute("xmlns:svg", "http://www.w3.org/2000/svg") svgBaseElement.setAttribute("xmlns:dc", "http://purl.org/dc/elements/1.1/") svgBaseElement.setAttribute("xmlns:cc", "http://creativecommons.org/ns#") svgBaseElement.setAttribute( "xmlns:rdf", "http://www.w3.org/1999/02/22-rdf-syntax-ns#") svgDefs = svgDoc.createElement("defs") svgSwatches = svgDoc.createElement("g") svgSwatches.setAttribute("id", "Swatches") svgMeta = svgDoc.createElement("metadata") svgBaseElement.appendChild(svgMeta) rdf = svgDoc.createElement("rdf:RDF") ccwork = svgDoc.createElement("cc:Work") dctitle = svgDoc.createElement("dc:title") dcdescription = svgDoc.createElement("dc:description") dctitle.appendChild(svgDoc.createTextNode(self.paletteName)) dcdescription.appendChild( svgDoc.createTextNode(self.currentPalette.comment())) ccwork.appendChild(dctitle) ccwork.appendChild(dcdescription) rdf.appendChild(ccwork) svgMeta.appendChild(rdf) Row = 0 Column = 0 iccProfileList = [] colorCount = self.currentPalette.colorsCountGroup("") for i in range(colorCount): entry = self.currentPalette.colorSetEntryFromGroup(i, "") color = self.currentPalette.colorForEntry(entry) iccColor = "icc-color(" + color.colorProfile() for c in range(len(color.componentsOrdered()) - 1): iccColor = "{col},{c}".format(col=iccColor, c=color.componentsOrdered()[c]) iccColor = iccColor + ")" if color.colorProfile() not in iccProfileList: iccProfileList.append(color.colorProfile()) # convert to sRGB color.setColorSpace("RGBA", "U8", "sRGB built-in") red = max(min(int(color.componentsOrdered()[0] * 255), 255), 0) green = max(min(int(color.componentsOrdered()[1] * 255), 255), 0) blue = max(min(int(color.componentsOrdered()[2] * 255), 255), 0) hexcode = "#{red:02x}{green:02x}{blue:02x}".format(red=red, green=green, blue=blue) swatchName = "{i}-{name}".format(i=i, name=entry.name()) swatchName = swatchName.replace(" ", "-") swatchName = swatchName.replace("(", "-") swatchName = swatchName.replace(")", "-") swatchMain = svgDoc.createElement("linearGradient") swatchMain.setAttribute("osb:paint", "solid") swatchMain.setAttribute("id", swatchName) swatchSub = svgDoc.createElement("stop") swatchSub.setAttribute( "style", "stop-color: {hex} {color};stop-opacity:1;".format( hex=hexcode, color=iccColor)) swatchMain.appendChild(swatchSub) svgDefs.appendChild(swatchMain) svgSingleSwatch = svgDoc.createElement("rect") svgSingleSwatch.setAttribute("x", str(int(Column * 20))) svgSingleSwatch.setAttribute("y", str(int(Row * 20))) svgSingleSwatch.setAttribute("width", str(int(20))) svgSingleSwatch.setAttribute("height", str(int(20))) svgSingleSwatch.setAttribute("fill", "url(#%s)" % swatchName) svgSingleSwatch.setAttribute("id", "swatch %s" % swatchName) if entry.spotColor() is True: svgSingleSwatch.setAttribute("rx", str(10)) svgSingleSwatch.setAttribute("ry", str(10)) svgSwatches.appendChild(svgSingleSwatch) Column += 1 if (Column >= self.currentPalette.columnCount()): Column = 0 Row += 1 groupNames = self.currentPalette.groupNames() for groupName in groupNames: Column = 0 Row += 1 groupTitle = svgDoc.createElement("text") groupTitle.setAttribute("x", str(int(Column * 20))) groupTitle.setAttribute("y", str(int(Row * 20) + 15)) groupTitle.appendChild(svgDoc.createTextNode(groupName)) svgSwatches.appendChild(groupTitle) Row += 1 colorCount = self.currentPalette.colorsCountGroup(groupName) for i in range(colorCount): entry = self.currentPalette.colorSetEntryFromGroup( i, groupName) color = self.currentPalette.colorForEntry(entry) iccColor = "icc-color(" + color.colorProfile() for c in range(len(color.componentsOrdered()) - 1): iccColor = "{col},{c}".format( col=iccColor, c=color.componentsOrdered()[c]) iccColor = iccColor + ")" if color.colorProfile() not in iccProfileList: iccProfileList.append(color.colorProfile()) # convert to sRGB color.setColorSpace("RGBA", "U8", "sRGB built-in") red = max(min(int(color.componentsOrdered()[0] * 255), 255), 0) green = max(min(int(color.componentsOrdered()[1] * 255), 255), 0) blue = max(min(int(color.componentsOrdered()[2] * 255), 255), 0) hexcode = "#{red:02x}{green:02x}{blue:02x}".format(red=red, green=green, blue=blue) swatchName = groupName + str(i) + "-" + entry.name() swatchName = swatchName.replace(" ", "-") swatchName = swatchName.replace("(", "-") swatchName = swatchName.replace(")", "-") swatchMain = svgDoc.createElement("linearGradient") swatchMain.setAttribute("osb:paint", "solid") swatchMain.setAttribute("id", swatchName) swatchSub = svgDoc.createElement("stop") swatchSub.setAttribute( "style", "stop-color: {hex} {color};stop-opacity:1;".format( hex=hexcode, color=iccColor)) swatchMain.appendChild(swatchSub) svgDefs.appendChild(swatchMain) svgSingleSwatch = svgDoc.createElement("rect") svgSingleSwatch.setAttribute("x", str(int(Column * 20))) svgSingleSwatch.setAttribute("y", str(int(Row * 20))) svgSingleSwatch.setAttribute("width", str(int(20))) svgSingleSwatch.setAttribute("height", str(int(20))) svgSingleSwatch.setAttribute("fill", "url(#%s)" % swatchName) svgSingleSwatch.setAttribute("id", "swatch %s" % swatchName) if entry.spotColor() is True: svgSingleSwatch.setAttribute("rx", str(10)) svgSingleSwatch.setAttribute("ry", str(10)) svgSwatches.appendChild(svgSingleSwatch) Column += 1 if (Column >= self.currentPalette.columnCount()): Column = 0 Row += 1 for profile in iccProfileList: svgProfileDesc = svgDoc.createElement("color-profile") svgProfileDesc.setAttribute("name", profile) # This is incomplete because python api doesn't have any # way to ask for this data yet. # svgProfileDesc.setAttribute("local", "sRGB") # svgProfileDesc.setAttribute("xlink:href", colorprofileurl) svgProfileDesc.setAttribute("rendering-intent", "perceptual") svgDefs.appendChild(svgProfileDesc) svgBaseElement.appendChild(svgDefs) svgBaseElement.appendChild(svgSwatches) svgBaseElement.setAttribute( "viewBox", "0 0 {cols} {row}".format( cols=self.currentPalette.columnCount() * 20, row=int((Row + 1) * 20))) svgDoc.appendChild(svgBaseElement) svgFile.write(svgDoc.toString()) svgFile.close()
def writeOutputFile(self, rasterLayer, outputFile, pointDistance, maxValueTolerance, startPoint, endPoint): resultXmlDocument = QDomDocument() encodingInstruction = resultXmlDocument.createProcessingInstruction( "encoding", "UTF-8") resultXmlDocument.appendChild(encodingInstruction) documentElement = resultXmlDocument.createElement("VFPData") resultXmlDocument.appendChild(documentElement) #profile length profileTotalDx = endPoint.x() - startPoint.x() profileTotalDy = endPoint.y() - startPoint.y() profileLength = math.sqrt(profileTotalDx * profileTotalDx + profileTotalDy * profileTotalDy) #single step dx = profileTotalDx / profileLength * pointDistance dy = profileTotalDy / profileLength * pointDistance dist = 0.0 lastDist = 0.0 currentValue = 0.0 sumDz = 0.0 #Just to check if sum(dz) equals (z - z_start) firstZ = self.firstRasterBandValue(startPoint, rasterLayer) if firstZ is None: #makes only sense if initial z is set QMessageBox.critical( None, QCoreApplication.translate("ProfileExportPlugin", "First z value invalid"), QCoreApplication.translate( "ProfileExportPlugin", "The first z-Value of the profile is invalid. Please make sure the profile start point is on the elevation model" )) return lastValue = firstZ currentX = startPoint.x() currentY = startPoint.y() while dist < profileLength: currentValue = self.firstRasterBandValue( QgsPointXY(currentX, currentY), rasterLayer) #elevation tolerance between two points exceeded. Insert additional points if not currentValue is None and not lastValue is None and ( currentValue - lastValue) > maxValueTolerance: nIntermediatePoints = int( (currentValue - lastValue) / maxValueTolerance) dIntermediatePointDist = math.sqrt( (dx / (nIntermediatePoints + 1)) * (dx / (nIntermediatePoints + 1)) + (dy / (nIntermediatePoints + 1)) * (dy / (nIntermediatePoints + 1))) lastIntermediateValue = lastValue for i in range(nIntermediatePoints): #print 'inserting additional point' dxIntermediate = dx / (nIntermediatePoints + 1) * (i + 1) dyIntermediate = dy / (nIntermediatePoints + 1) * (i + 1) xIntermediate = currentX - dx + dxIntermediate yIntermediate = currentY - dy + dyIntermediate intermediateDist = math.sqrt( dxIntermediate * dxIntermediate + dyIntermediate * dyIntermediate) currentIntermediateValue = self.firstRasterBandValue( QgsPointXY(xIntermediate, yIntermediate), rasterLayer) if not currentIntermediateValue is None and not lastValue is None: self.addElevationPoint( resultXmlDocument, documentElement, dist - pointDistance + intermediateDist, dIntermediatePointDist, currentIntermediateValue - lastValue, currentIntermediateValue - firstZ, xIntermediate, yIntermediate) sumDz = sumDz + (currentIntermediateValue - lastValue) lastValue = currentIntermediateValue lastDist = dist - pointDistance + intermediateDist if not currentValue is None and not lastValue is None: self.addElevationPoint(resultXmlDocument, documentElement, dist, dist - lastDist, currentValue - lastValue, currentValue - firstZ, currentX, currentY) sumDz = sumDz + currentValue - lastValue currentX += dx currentY += dy lastDist = dist dist += pointDistance lastValue = currentValue #last value normally does not fit into the point interval if currentX != endPoint.x() or currentY != entPoint.y(): currentValue = self.firstRasterBandValue(endPoint, rasterLayer) if not currentValue is None: self.addElevationPoint(resultXmlDocument, documentElement, profileLength, pointDistance - (dist - profileLength), currentValue - lastValue, currentValue - firstZ, endPoint.x(), endPoint.y()) sumDz = sumDz + currentValue - lastValue #debug #print( 'sumDz: {}'.format( sumDz ) ) #print( 'z0 : {}'.format( currentValue - firstZ ) ) #write dom document to file resultXmlFile = QFile(outputFile) if not resultXmlFile.open(QIODevice.WriteOnly): QMessageBox.critical( None, QCoreApplication.translate("ProfileExportPlugin", "Error"), QCoreApplication.translate( "ProfileExportPlugin", "The output file could not be written to disk")) return resultTextStream = QTextStream(resultXmlFile) resultTextStream.setCodec("UTF-8") resultTextStream.__lshift__(resultXmlDocument.toString()) resultXmlFile.close() if abs(sumDz - (currentValue - firstZ)) > 0.000001: QMessageBox.critical( None, QCoreApplication.translate("ProfileExportPlugin", "Error"), QCoreApplication.translate( "ProfileExportPlugin", "An error occured during checking the written elevation values. The values might not be correct" )) else: QMessageBox.information( None, QCoreApplication.translate("ProfileExportPlugin", "Export finished"), QCoreApplication.translate( "ProfileExportPlugin", "The profile export is successfully finished"))
class MultiDaemonFile: file_path = '/tmp/RaySession/multi-daemon.xml' def __init__(self, session, server): self.session = session self.server = server self.xml = QDomDocument() global instance instance = self @staticmethod def getInstance(): return instance def pidExists(self, pid): if isinstance(pid, str): pid = int(pid) try: os.kill(pid, 0) except OSError: return False else: return True def removeFile(self): try: os.remove(self.file_path) except: return def openFile(self): if not os.path.exists(self.file_path): if not os.path.exists(os.path.dirname(self.file_path)): os.makedirs(os.path.dirname(self.file_path)) return False try: file = open(self.file_path, 'r') self.xml.setContent(file.read()) file.close() return True except: self.removeFile() return False def writeFile(self): try: file = open(self.file_path, 'w') file.write(self.xml.toString()) file.close() except: return def setAttributes(self, element): element.setAttribute('net_daemon_id', self.server.net_daemon_id) element.setAttribute('root', self.session.root) element.setAttribute('session_path', self.session.path) element.setAttribute('pid', os.getpid()) element.setAttribute('port', self.server.port) element.setAttribute('user', os.getenv('USER')) element.setAttribute( 'not_default', int(bool(self.server.is_nsm_locked or self.server.not_default))) element.setAttribute('has_gui', int(self.server.hasGui())) element.setAttribute('version', ray.VERSION) def update(self): has_dirty_pid = False if not self.openFile(): ds = self.xml.createElement('Daemons') dm_xml = self.xml.createElement('Daemon') self.setAttributes(dm_xml) ds.appendChild(dm_xml) self.xml.appendChild(ds) else: found = False xml_content = self.xml.documentElement() nodes = xml_content.childNodes() for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() pid = dxe.attribute('pid') if pid.isdigit() and pid == str(os.getpid()): self.setAttributes(dxe) found = True elif not pid.isdigit() or not self.pidExists(int(pid)): has_dirty_pid = True if not found: dm_xml = self.xml.createElement('Daemon') self.setAttributes(dm_xml) self.xml.firstChild().appendChild(dm_xml) if has_dirty_pid: self.cleanDirtyPids() self.writeFile() def quit(self): if not self.openFile(): return xml_content = self.xml.documentElement() nodes = xml_content.childNodes() for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() pid = dxe.attribute('pid') if pid.isdigit() and pid == str(os.getpid()): break else: return xml_content.removeChild(node) self.writeFile() def isFreeForRoot(self, daemon_id, root_path): if not self.openFile(): return True xml_content = self.xml.documentElement() nodes = xml_content.childNodes() for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() if (dxe.attribute('net_daemon_id') == str(daemon_id) and dxe.attribute('root') == root_path): pid = dxe.attribute('pid') if pid.isdigit() and self.pidExists(int(pid)): return False return True def isFreeForSession(self, session_path): if not self.openFile(): return True xml_content = self.xml.documentElement() nodes = xml_content.childNodes() for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() if dxe.attribute('session_path') == session_path: pid = dxe.attribute('pid') if pid.isdigit() and self.pidExists(int(pid)): return False return True def getAllSessionPaths(self): if not self.openFile(): return [] all_session_paths = [] xml_content = self.xml.documentElement() nodes = xml_content.childNodes() for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() spath = dxe.attribute('session_path') pid = dxe.attribute('pid') if spath and pid.isdigit() and self.pidExists(int(pid)): all_session_paths.append(spath) return all_session_paths def cleanDirtyPids(self): xml_content = self.xml.documentElement() nodes = xml_content.childNodes() rm_nodes = [] for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() pid = dxe.attribute('pid') if not pid.isdigit() or not self.pidExists(int(pid)): rm_nodes.append(node) for node in rm_nodes: xml_content.removeChild(node) def getDaemonList(self): daemon_list = [] has_dirty_pid = False if not self.openFile(): return daemon_list xml_content = self.xml.documentElement() nodes = xml_content.childNodes() for i in range(nodes.count()): node = nodes.at(i) dxe = node.toElement() daemon = Daemon() daemon.root = dxe.attribute('root') daemon.session_path = dxe.attribute('session_path') daemon.user = dxe.attribute('user') daemon.not_default = bool(dxe.attribute('not_default') == 'true') net_daemon_id = dxe.attribute('net_daemon_id') pid = dxe.attribute('pid') port = dxe.attribute('port') if net_daemon_id.isdigit(): daemon.net_daemon_id = net_daemon_id if pid.isdigit(): daemon.pid = pid if port.isdigit(): daemon.port = port if not self.pidExists(daemon.pid): has_dirty_pid = True continue if not (daemon.net_daemon_id and daemon.pid and daemon.port): continue daemon_list.append(daemon) if has_dirty_pid: self.cleanDirtyPids() return daemon_list
def export(configDictionary={}, projectURL=str(), pagesLocationList=[], pageData=[]): path = Path(os.path.join(projectURL, configDictionary["exportLocation"])) exportPath = path / "EPUB-files" metaInf = exportPath / "META-INF" oebps = exportPath / "OEBPS" imagePath = oebps / "Images" # Don't write empty folders. Epubcheck doesn't like that. # stylesPath = oebps / "Styles" textPath = oebps / "Text" if exportPath.exists() is False: exportPath.mkdir() metaInf.mkdir() oebps.mkdir() imagePath.mkdir() # stylesPath.mkdir() textPath.mkdir() # Due the way EPUB verifies, the mimetype needs to be packaged in first. # Due the way zips are constructed, the only way to ensure that is to # Fill the zip as we go along... # Use the project name if there's no title to avoid sillyness with unnamed zipfiles. title = configDictionary["projectName"] if "title" in configDictionary.keys(): title = str(configDictionary["title"]).replace(" ", "_") # Get the appropriate path. url = str(path / str(title + ".epub")) # Create a zip file. epubArchive = zipfile.ZipFile(url, mode="w", compression=zipfile.ZIP_STORED) mimetype = open(str(Path(exportPath / "mimetype")), mode="w") mimetype.write("application/epub+zip") mimetype.close() # Write to zip. epubArchive.write(Path(exportPath / "mimetype"), Path("mimetype")) container = QDomDocument() cRoot = container.createElement("container") cRoot.setAttribute("version", "1.0") cRoot.setAttribute("xmlns", "urn:oasis:names:tc:opendocument:xmlns:container") container.appendChild(cRoot) rootFiles = container.createElement("rootfiles") rootfile = container.createElement("rootfile") rootfile.setAttribute("full-path", "OEBPS/content.opf") rootfile.setAttribute("media-type", "application/oebps-package+xml") rootFiles.appendChild(rootfile) cRoot.appendChild(rootFiles) containerFileName = str(Path(metaInf / "container.xml")) containerFile = open(containerFileName, 'w', newline="", encoding="utf-8") containerFile.write(container.toString(indent=2)) containerFile.close() # Write to zip. epubArchive.write(containerFileName, os.path.relpath(containerFileName, str(exportPath))) # copyimages to images pagesList = [] if len(pagesLocationList) > 0: if "cover" in configDictionary.keys(): coverNumber = configDictionary["pages"].index( configDictionary["cover"]) else: coverNumber = 0 for p in pagesLocationList: if os.path.exists(p): shutil.copy2(p, str(imagePath)) filename = str(Path(imagePath / os.path.basename(p))) pagesList.append(filename) epubArchive.write(filename, os.path.relpath(filename, str(exportPath))) if len(pagesLocationList) >= coverNumber: coverpageurl = pagesList[coverNumber] else: print("CPMT: Couldn't find the location for the epub images.") return False # for each image, make an xhtml file htmlFiles = [] listOfNavItems = {} listofSpreads = [] regions = [] for i in range(len(pagesList)): pageName = "Page" + str(i) + ".xhtml" doc = QDomDocument() html = doc.createElement("html") doc.appendChild(html) html.setAttribute("xmlns", "http://www.w3.org/1999/xhtml") html.setAttribute("xmlns:epub", "http://www.idpf.org/2007/ops") # The viewport is a prerequisite to get pre-paginated # layouts working. We'll make the layout the same size # as the image. head = doc.createElement("head") viewport = doc.createElement("meta") viewport.setAttribute("name", "viewport") img = QImage() img.load(pagesLocationList[i]) w = img.width() h = img.height() widthHeight = "width=" + str(w) + ", height=" + str(h) viewport.setAttribute("content", widthHeight) head.appendChild(viewport) html.appendChild(head) # Here, we process the region navigation data to percentages # because we have access here to the width and height of the viewport. data = pageData[i] transform = data["transform"] for v in data["vector"]: pointsList = [] dominantColor = QColor(Qt.white) listOfColors = [] for point in v["boundingBox"]: offset = QPointF(transform["offsetX"], transform["offsetY"]) pixelPoint = QPointF(point.x() * transform["resDiff"], point.y() * transform["resDiff"]) newPoint = pixelPoint - offset x = max(0, min(w, int(newPoint.x() * transform["scaleWidth"]))) y = max(0, min(h, int(newPoint.y() * transform["scaleHeight"]))) listOfColors.append(img.pixelColor(QPointF(x, y).toPoint())) pointsList.append(QPointF((x / w) * 100, (y / h) * 100)) regionType = "panel" if "text" in v.keys(): regionType = "text" if len(listOfColors) > 0: dominantColor = listOfColors[-1] listOfColors = listOfColors[:-1] for color in listOfColors: dominantColor.setRedF( 0.5 * (dominantColor.redF() + color.redF())) dominantColor.setGreenF( 0.5 * (dominantColor.greenF() + color.greenF())) dominantColor.setBlueF( 0.5 * (dominantColor.blueF() + color.blueF())) region = {} bounds = QPolygonF(pointsList).boundingRect() region["points"] = bounds region["type"] = regionType region["page"] = str(Path(textPath / pageName)) region["primaryColor"] = dominantColor.name() regions.append(region) # We can also figureout here whether the page can be seen as a table of contents entry. if "acbf_title" in data["keys"]: listOfNavItems[str(Path(textPath / pageName))] = data["title"] # Or spreads... if "epub_spread" in data["keys"]: listofSpreads.append(str(Path(textPath / pageName))) body = doc.createElement("body") img = doc.createElement("img") img.setAttribute("src", os.path.relpath(pagesList[i], str(textPath))) body.appendChild(img) html.appendChild(body) filename = str(Path(textPath / pageName)) docFile = open(filename, 'w', newline="", encoding="utf-8") docFile.write(doc.toString(indent=2)) docFile.close() if pagesList[i] == coverpageurl: coverpagehtml = os.path.relpath(filename, str(oebps)) htmlFiles.append(filename) # Write to zip. epubArchive.write(filename, os.path.relpath(filename, str(exportPath))) # metadata filename = write_opf_file(oebps, configDictionary, htmlFiles, pagesList, coverpageurl, coverpagehtml, listofSpreads) epubArchive.write(filename, os.path.relpath(filename, str(exportPath))) filename = write_region_nav_file(oebps, configDictionary, htmlFiles, regions) epubArchive.write(filename, os.path.relpath(filename, str(exportPath))) # toc filename = write_nav_file(oebps, configDictionary, htmlFiles, listOfNavItems) epubArchive.write(filename, os.path.relpath(filename, str(exportPath))) filename = write_ncx_file(oebps, configDictionary, htmlFiles, listOfNavItems) epubArchive.write(filename, os.path.relpath(filename, str(exportPath))) epubArchive.close() return True
class EditSelfDefineFormatDetailModule(QDialog, Ui_Dialog): def __init__(self, autoid=None, parent=None): super(EditSelfDefineFormatDetailModule, self).__init__(parent) self.setupUi(self) self.setWindowFlag(Qt.WindowMinMaxButtonsHint) if '3' not in user.powers: self.close() if user.powers['3'] == 0: self.close() self.power = '{:03b}'.format(user.powers['3']) if self.power[1] == '0': self.pushButton_accept.setEnabled(False) self.pushButton_close.setEnabled(False) self.autoid = autoid self.detail = QWidget() self.dom = QDomDocument() self.current_widget = QWidget() self.nodelist = None self.SC = SelfdefinedformatController() self.ori_detail = {} self.new_detail = {} self.format_content = '<?xml version="1.0"?><GMPPaper />' self.current_content = XMLReadWrite() self.current_elemnt = None res = self.get_detail() self.set_kind() self.set_subkind() if res: self.set_formtype() self.set_widgetlist() self.set_format() for i in range(0, 17): getattr(self, 'checkBox_' + str(2**i)).toggled.connect( self.on_formattype_toggled) def get_detail(self): if self.autoid is None: return False condition = {'autoid': self.autoid} res = self.SC.get_data(0, False, *VALUES_TUPLE_SD, **condition) if not len(res): return self.ori_detail = res[0] self.lineEdit_formatname.setText(self.ori_detail['formatname']) self.comboBox_orientation.setCurrentIndex( self.ori_detail['orientation']) self.checkBox_flag.setChecked(self.ori_detail['flag']) self.format_content = self.ori_detail['format'] return True def set_kind(self): items = self.SC.get_data(0, True, *VALUES_TUPLE_KIND).distinct() if len(items): self.comboBox_kind.addItems(items) if len(self.ori_detail): self.comboBox_kind.setCurrentText(self.ori_detail['kind']) else: self.comboBox_kind.setCurrentText('') def set_subkind(self): items = self.SC.get_data(0, True, *VALUES_TUPLE_SUBKIND).distinct() if len(items): self.comboBox_subkind.addItems(items) if len(self.ori_detail): self.comboBox_subkind.setCurrentText(self.ori_detail['subkind']) else: self.comboBox_subkind.setCurrentText('') def set_formtype(self): if self.ori_detail['formtype'] == 0: return formtype = '{:017b}'.format(self.ori_detail['formtype']) for i in range(0, 17): getattr(self, 'checkBox_' + str(2**i)).setChecked(int(formtype[i])) def set_format(self): if not self.gridLayout_5.isEmpty(): # self.gridLayout_5.removeWidget(self.current_content) self.format_content = self.dom.toString(-1) self.current_content.clear() self.current_content.scrollArea.setHidden(True) else: self.gridLayout_5.addWidget(self.current_content) self.current_content.openxml(self.format_content, True) self.current_content.scrollArea.setHidden(False) def set_widgetlist(self): self.treeWidget_widgetlist.clear() file = self.format_content qfile = QFile(file) self.dom = QDomDocument() # 找到文件,则设置引擎,否则向xml文件直接添加数据 if qfile.open(QFile.ReadWrite | QFile.Text): self.dom.setContent(QFile) # self.file = QFile else: self.dom.setContent(file) # self.file = file if self.dom.isNull(): return False # 获得根目录的元素,返回QDomElement <GMPPaper> element = self.dom.documentElement() # 获得第一个子元素,返回QDomNode n = element.firstChild() # 如果没有读到文档结尾,而且没有出现错误 self.nodelist = element.childNodes() line_number = 1 for i in range(len(self.nodelist)): tag_name = self.nodelist.item(i).toElement().tagName() qtreeitem = QTreeWidgetItem(self.treeWidget_widgetlist) qtreeitem.setText(0, str(i)) qtreeitem.setText(1, str(line_number)) qtreeitem.setText(2, TAG_NAME_DICT[tag_name]) if tag_name == "br": line_number += 1 if qfile.isOpen(): qfile.close() @pyqtSlot(QTreeWidgetItem, int) def on_treeWidget_widgetlist_itemClicked(self, qtreeitem, p_int): index = int(qtreeitem.text(0)) childrens = self.current_content.scrollAreaWidgetContents.children() item = childrens[index] item.setFocus() self.showsetting(item) @pyqtSlot(QMouseEvent) def mouseDoubleClickEvent(self, event): pos = event.pos() widget = self.childAt(pos) super(EditSelfDefineFormatDetailModule, self).mouseDoubleClickEvent(event) def mousePressEvent(self, event): pos = event.pos() widget = self.childAt(pos) self.showsetting(widget) def showsetting(self, widget): if not hasattr(widget, 'index') or self.current_widget == widget: self.current_elemnt = None return try: self.current_widget.leave() except AttributeError: if hasattr(self.current_widget.parent(), 'leave'): self.current_widget.parent().leave() except RuntimeError: pass self.current_widget = widget index = widget.index item = self.treeWidget_widgetlist.topLevelItem(index) if not self.gridLayout_6.isEmpty(): self.gridLayout_6.removeWidget(self.detail) self.detail.close() self.treeWidget_widgetlist.setCurrentItem(item) self.current_elemnt = self.nodelist.item(index).toElement() if self.current_elemnt.tagName() not in WIDGET_TYPE: self.detail.close() return self.detail = WIDGET_TYPE[self.current_elemnt.tagName()]( self.current_elemnt, self) self.detail.edited.connect(self.set_format) self.gridLayout_6.addWidget(self.detail) @pyqtSlot() def on_pushButton_1_clicked(self): new_element = self.dom.createElement("Title") new_element.setAttribute("width", 18) text = self.dom.createTextNode("新标题") new_element.appendChild(text) if self.current_elemnt is None or not hasattr(self.current_elemnt, 'tagName'): self.dom.documentElement().appendChild(new_element) else: self.dom.documentElement().insertBefore(new_element, self.current_elemnt) self.flush() @pyqtSlot() def on_pushButton_2_clicked(self): new_element = self.dom.createElement("TextBox") new_element.setAttribute("width", 30) if self.current_elemnt is None: self.dom.documentElement().appendChild(new_element) else: self.dom.documentElement().insertBefore(new_element, self.current_elemnt) self.flush() @pyqtSlot() def on_pushButton_3_clicked(self): new_element = self.dom.createElement("Signature") new_element.setAttribute("width", 30) if self.current_elemnt is None: self.dom.documentElement().appendChild(new_element) else: self.dom.documentElement().insertBefore(new_element, self.current_elemnt) self.flush() @pyqtSlot() def on_pushButton_4_clicked(self): new_element = self.dom.createElement("Memo") new_element.setAttribute("width", 50) new_element.setAttribute("height", 3) if self.current_elemnt is None: self.dom.documentElement().appendChild(new_element) else: self.dom.documentElement().insertBefore(new_element, self.current_elemnt) self.flush() @pyqtSlot() def on_pushButton_5_clicked(self): new_element = self.dom.createElement("ComboBox") new_element.setAttribute("width", 30) if self.current_elemnt is None: self.dom.documentElement().appendChild(new_element) else: self.dom.documentElement().insertBefore(new_element, self.current_elemnt) self.flush() @pyqtSlot() def on_pushButton_6_clicked(self): new_element = self.dom.createElement("CheckBox") new_element.setAttribute("width", 30) if self.current_elemnt is None: self.dom.documentElement().appendChild(new_element) else: self.dom.documentElement().insertBefore(new_element, self.current_elemnt) self.flush() @pyqtSlot() def on_pushButton_7_clicked(self): new_element = self.dom.createElement("Box") new_element.setAttribute("width", 50) new_element.setAttribute("height", 3) new_element.setAttribute("PenWidth", 2) if self.current_elemnt is None: self.dom.documentElement().appendChild(new_element) else: self.dom.documentElement().insertBefore(new_element, self.current_elemnt) self.flush() @pyqtSlot() def on_pushButton_8_clicked(self): new_element = self.dom.createElement("Expr") new_element.setAttribute("width", 30) if self.current_elemnt is None: self.dom.documentElement().appendChild(new_element) else: self.dom.documentElement().insertBefore(new_element, self.current_elemnt) self.flush() @pyqtSlot() def on_pushButton_9_clicked(self): new_element = self.dom.createElement("br") # new_element.setAttribute("width", 20) if self.current_elemnt is None: self.dom.documentElement().appendChild(new_element) else: self.dom.documentElement().insertBefore(new_element, self.current_elemnt) self.flush() @pyqtSlot() def on_pushButton_10_clicked(self): if self.current_widget is None or not hasattr(self.current_widget, 'index'): return index = self.current_widget.index self.nodelist.item(index) try: self.dom.documentElement().removeChild(self.current_elemnt) except TypeError: pass self.flush() def flush(self): # index = self.treeWidget_widgetlist.currentIndex().data(Qt.DisplayRole) current_item = self.treeWidget_widgetlist.currentItem() if current_item is None: index = None else: index = current_item.text(0) self.set_format() self.set_widgetlist() if index is not None: self.current_elemnt = self.nodelist.item(int(index)) newindex = self.treeWidget_widgetlist.model().index(int(index), 0) try: self.current_content.scrollAreaWidgetContents.children()[int( index)].setFocus() except IndexError: pass else: count = self.treeWidget_widgetlist.topLevelItemCount() self.current_elemnt = self.nodelist.item(count - 1) newindex = self.treeWidget_widgetlist.model().index(count - 1, 0) try: self.current_content.scrollAreaWidgetContents.children()[ count - 1].setFocus() except IndexError: pass self.treeWidget_widgetlist.setCurrentIndex(newindex) @pyqtSlot(str) def on_lineEdit_formatname_textChanged(self, p_str): try: if p_str != self.ori_detail['formatname']: self.new_detail['formatname'] = p_str else: try: del self.new_detail['formatname'] except KeyError: pass except KeyError: self.new_detail['formatname'] = p_str @pyqtSlot(str) def on_comboBox_kind_currentTextChanged(self, p_str): try: if p_str != self.ori_detail['kind']: self.new_detail['kind'] = p_str else: try: del self.new_detail['kind'] except KeyError: pass except KeyError: self.new_detail['kind'] = p_str @pyqtSlot(str) def on_comboBox_subkind_currentTextChanged(self, p_str): try: if p_str != self.ori_detail['subkind']: self.new_detail['subkind'] = p_str else: try: del self.new_detail['subkind'] except KeyError: pass except KeyError: self.new_detail['subkind'] = p_str @pyqtSlot(int) def on_comboBox_orientation_currentIndexChanged(self, p_int): try: if p_int != self.ori_detail['orientation']: self.new_detail['orientation'] = p_int else: try: del self.new_detail['orientation'] except KeyError: pass except KeyError: self.new_detail['orientation'] = p_int @pyqtSlot(bool) def on_checkBox_flag_toggled(self, p_bool): p_int = 1 if p_bool else 0 try: if p_int != self.ori_detail['flag']: self.new_detail['flag'] = p_int else: try: del self.new_detail['flag'] except KeyError: pass except KeyError: self.new_detail['flag'] = p_int @pyqtSlot(bool) def on_formattype_toggled(self, p_bool): combobox = self.sender() try: num = int( combobox.objectName().split("_")[1]) * (1 if p_bool else -1) except (IndexError, ValueError): return if 'formtype' in self.new_detail: self.new_detail['formtype'] += num elif len(self.ori_detail): self.new_detail['formtype'] = self.ori_detail['formtype'] + num else: self.new_detail['formtype'] = num @pyqtSlot() def on_pushButton_accept_clicked(self): xml = self.dom.toString(-1) self.new_detail['format'] = xml if self.autoid is not None: condition = {'autoid': self.autoid} self.SC.update_data(0, condition=condition, **self.new_detail) else: self.SC.update_data(0, **self.new_detail) self.accept() @pyqtSlot() def on_pushButton_view_clicked(self): detail = ViewFormat(self.dom, self) detail.show() @pyqtSlot() def on_pushButton_cancel_clicked(self): self.close()
def SeveToFile(self, path): #print(path) f = QFile(path) if f.open(QIODevice.WriteOnly): stream = QTextStream(f) stream.setCodec("UTF-8") doc = QDomDocument() xmlInstruct = doc.createProcessingInstruction( "xml", "version=\"1\" encoding=\"UTF-8\"") doc.appendChild(xmlInstruct) mainEl = doc.createElement("Nodes") doc.appendChild(mainEl) for i in range(0, len(self.nodes)): objectEl = doc.createElement("Node") mainEl.appendChild(objectEl) idoEl = doc.createElement("Id") objectEl.appendChild(idoEl) idoEltext = doc.createTextNode(str(i)) idoEl.appendChild(idoEltext) typeEl = doc.createElement("Type") objectEl.appendChild(typeEl) nameEltext = doc.createTextNode(type(self.nodes[i]).__name__) typeEl.appendChild(nameEltext) posEl = doc.createElement("Pos") objectEl.appendChild(posEl) pos = self.nodes[i].item.scenePos() posEltext = doc.createTextNode( str(pos.x()) + "," + str(pos.y())) posEl.appendChild(posEltext) liksEl = doc.createElement("Links") objectEl.appendChild(liksEl) inputs = self.nodes[i].inputs for j in range(0, len(inputs)): if inputs[j].node is not None: linkEl = doc.createElement("Link") liksEl.appendChild(linkEl) idEl = doc.createElement("Id") linkEl.appendChild(idEl) idEltext = doc.createTextNode(str(j)) idEl.appendChild(idEltext) nodeEl = doc.createElement("Node") linkEl.appendChild(nodeEl) idnEltext = doc.createTextNode( str(self.indexOfNode(inputs[j].node))) nodeEl.appendChild(idnEltext) outEl = doc.createElement("Out") linkEl.appendChild(outEl) outEltext = doc.createTextNode(str(inputs[j].out)) outEl.appendChild(outEltext) doc.save(stream, 4) f.close() return True return False