浏览代码

FIX Escape regex special cars

olivier.massot 7 年之前
父节点
当前提交
891d2cccc8
共有 6 个文件被更改,包括 174 次插入17 次删除
  1. 38 13
      Viewer.py
  2. 6 2
      core.py
  3. 0 1
      main.py
  4. 1 1
      qt_viewer.ui
  5. 129 0
      test/source/tables/Avec[92][47][63]caractères_spéciaux.xml
  6. 二进制
      test/test.zip

+ 38 - 13
Viewer.py

@@ -2,14 +2,15 @@
 @author: olivier.massot
 '''
 
-from PyQt5 import uic
+from PyQt5 import uic, QtCore
 from PyQt5.Qt import Qt, QEvent, QGraphicsScene, QPointF, QFileDialog, \
     QApplication, QMessageBox, QTreeWidgetItem, \
     QGraphicsTextItem, QGraphicsItem, QGraphicsRectItem, \
     QBrush, QColor, QGraphicsLineItem, QLineF, \
     QPen, QPainter, QSvgGenerator, QSize, QRect, QGraphicsItemGroup, \
     QGraphicsColorizeEffect, QFont, QDialog, QTableWidgetItem, \
-    QListWidgetItem, QInputDialog, QIcon, QPixmap
+    QListWidgetItem, QInputDialog, QIcon, QPixmap, pyqtSignal, QObject, \
+    QTreeWidgetItemIterator
 from PyQt5.QtWidgets import QMainWindow, QGraphicsView
 from path import Path
 
@@ -35,8 +36,12 @@ v_spacing = 120
 cell_width = 150
 cell_spacing = 25
 
+
+
+
 class GraphicsObject(QGraphicsItemGroup):
     items = []
+
     def __init__(self, obj, parent=None):
         super(GraphicsObject, self).__init__(parent=parent)
         self.obj = obj
@@ -115,6 +120,9 @@ class GraphicsObject(QGraphicsItemGroup):
     def hoverLeaveEvent(self, _):
         self.setShining(False)
 
+    def mouseDoubleClickEvent(self, _):
+        self.scene().itemDoubleClicked.emit(self)
+
 class GraphicsRootObject(GraphicsObject):
     def __init__(self, obj, parent=None):
         super(GraphicsRootObject, self).__init__(obj, parent=parent)
@@ -263,6 +271,10 @@ class GraphicsLink(QGraphicsLineItem):
         line = QLineF(self.mapToScene(self.topGraphicsObject.bottomAnchorCenter()), self.mapToScene(self.bottomGraphicsObject.topAnchorCenter()))
         self.setLine(line)
 
+class GraphicsScene(QGraphicsScene):
+    itemDoubleClicked = pyqtSignal(object)
+
+
 class Viewer(QMainWindow):
 
     def __init__(self):
@@ -302,8 +314,9 @@ class Viewer(QMainWindow):
         self.ui.view.setTransformationAnchor(QGraphicsView.AnchorUnderMouse)
         self.ui.view.viewport().installEventFilter(self)
 
-        self._scene = QGraphicsScene()
+        self._scene = GraphicsScene()
         self._scene.setItemIndexMethod(QGraphicsScene.BspTreeIndex)
+        self._scene.itemDoubleClicked.connect(self.graphicsObjectDoubleClicked)
 
         self.ui.view.setScene(self._scene)
 
@@ -451,9 +464,13 @@ class Viewer(QMainWindow):
         GraphicsObject.items = []
         self.enable_view_buttons(False)
 
-    def maj_view_with(self, root_object):
+    def update_view(self, root_object=None):
+        if root_object is None:
+            root_object = next((go.obj for go in GraphicsObject.items if type(go) is GraphicsRootObject))
+
         self.switch_graphic_view()
         self.clear_scene()
+
         root = GraphicsRootObject(root_object)
         self._scene.addItem(root)
 
@@ -522,7 +539,7 @@ class Viewer(QMainWindow):
             self.ui.btn_edit_item.setEnabled(False)
             return
         obj = core.Analyse.objects[index]
-        self.maj_view_with(obj)
+        self.update_view(obj)
         self.ui.btn_edit_item.setEnabled(True)
 
     def filterTblDeps(self, filterStr):
@@ -552,19 +569,29 @@ class Viewer(QMainWindow):
         self.ui.treeWidget.setCurrentItem(match)
         self.ui.treeWidget.scrollTo(self.ui.treeWidget.indexFromItem(match, 1))
 
-    def edit_selected_item(self):
-        index = self.ui.treeWidget.currentItem().data(2, 0)
-        obj = core.Analyse.objects[index]
+    def edit(self, obj):
         dlg = DetailsDialog(obj, self)
         dlg.show()
         r = dlg.exec_()
         if r:
             core.Analyse.build_trees()
-            self.maj_view_with(obj)
+            self.update_view()
+            item = self.find_tree_item(obj)
             if any(len(m.warnings) > 0 for m in obj.mentions):
-                self.ui.treeWidget.currentItem().setIcon(0, QIcon(QPixmap(core.here / "rsc\\warning_16.png")))
+                item.setIcon(0, QIcon(QPixmap(core.here / "rsc\\warning_16.png")))
             else:
-                self.ui.treeWidget.currentItem().setIcon(0, QIcon())
+                item.setIcon(0, QIcon())
+
+    def find_tree_item(self, obj):
+        return next((item for item in self.ui.treeWidget.findItems("", Qt.MatchContains | Qt.MatchRecursive, 1) if item.data(2, 0) == core.Analyse.objects.index(obj)))
+
+    def edit_selected_item(self):
+        index = self.ui.treeWidget.currentItem().data(2, 0)
+        obj = core.Analyse.objects[index]
+        self.edit(obj)
+
+    def graphicsObjectDoubleClicked(self, go):
+        self.edit(go.obj)
 
     def keyPressEvent(self, e):
         if e.key() == Qt.Key_S and e.modifiers() & Qt.ControlModifier:
@@ -578,8 +605,6 @@ class Viewer(QMainWindow):
         if e.key() == Qt.Key_Control:
             self.ui.view.setDragMode(QGraphicsView.RubberBandDrag)
 
-
-
 class DetailsDialog(QDialog):
 
     def __init__(self, obj, parent=None):

+ 6 - 2
core.py

@@ -72,6 +72,10 @@ class AccessObject():
     def __repr__(self):
         return "<{}: {}>".format(self.type_, self.name_)
 
+    def rxname(self):
+        return self.name_.lower().replace("?", "\?").replace(".", "\.").replace("")
+
+
     @classmethod
     def from_file(cls, file):
         file = Path(file)
@@ -207,14 +211,14 @@ class Analyse():
     def parse_source(cls, subject):
 
         # On cherche le nom de chaque autre objet, ainsi que le nom des fonctions issues des modules
-        look_for = {obj.name_ for obj in cls.objects if obj is not subject and type(object) is not ModuleObject} | set(sum([obj.functions for obj in cls.objects if obj is not subject], []))
+        look_for = {re.escape(obj.name_) for obj in cls.objects if obj is not subject and type(object) is not ModuleObject} | set(sum([obj.functions for obj in cls.objects if obj is not subject], []))
 
         names = "|".join(list(look_for))
         seps = "|".join(("\t", " ", "\[", "\]", "&", "\(", "\)", "\.", "!", "'", "\"", r"\\015", r"\\012"))  # Note: Les separateurs possibles incluent \015 et \012 qui sont les hexadecimaux pour \n et \r
 
         rstr = """(?:^|{seps})({names})(?:$|{seps})""".format(seps=seps, names=names)
 
-        rx = re.compile(rstr, MULTILINE | IGNORECASE | VERBOSE)
+        rx = re.compile(rstr, MULTILINE | IGNORECASE)
 
         # Indexe la position des lignes
         line_matches = list(re.finditer('.*\n', subject.sourcecode))

+ 0 - 1
main.py

@@ -7,7 +7,6 @@ from PyQt5.Qt import QApplication, QMessageBox
 
 from Viewer import Viewer
 
-# TODO: editer un objet sur double-clic sur l'item graphique
 # TODO: Permettre de limiter le nombre d'"étages" à afficher
 # TODO: Dans le TreeWidget: aficher la liste des fonctons à la place de celle des modules, sous la forme "Module.fonction"
 

+ 1 - 1
qt_viewer.ui

@@ -217,7 +217,7 @@
         <item>
          <widget class="QStackedWidget" name="stackedView">
           <property name="currentIndex">
-           <number>1</number>
+           <number>0</number>
           </property>
           <widget class="QWidget" name="page_3">
            <layout class="QHBoxLayout" name="horizontalLayout_6">

+ 129 - 0
test/source/tables/Avec[92][47][63]caractères_spéciaux.xml

@@ -0,0 +1,129 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<root xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:od="urn:schemas-microsoft-com:officedata">
+<xsd:schema>
+<xsd:element name="dataroot">
+<xsd:complexType>
+<xsd:sequence>
+<xsd:element ref="Avec_x005C__x002F__x003F_caractères_spéciaux" minOccurs="0" maxOccurs="unbounded"/>
+</xsd:sequence>
+<xsd:attribute name="generated" type="xsd:dateTime"/>
+</xsd:complexType>
+</xsd:element>
+<xsd:element name="Avec_x005C__x002F__x003F_caractères_spéciaux">
+<xsd:annotation>
+<xsd:appinfo>
+<od:tableProperty name="GUID" type="9" value="9DcYIYnlakO4qwMiI/6pdQ==
+"/>
+<od:tableProperty name="Orientation" type="2" value="0"/>
+<od:tableProperty name="OrderByOn" type="1" value="0"/>
+<od:tableProperty name="NameMap" type="11" value="CswOVQAAAAD0NxghieVqQ7irAyIj/ql1AAAAANmSkAqNFuVAAAAAAAAAAABBAHYA
+ZQBjAFwALwA/AGMAYQByAGEAYwB0AOgAcgBlAHMAIgBzAHAA6QBjAGkAYQB1AHgA
+AAAAAAAAiZwMcYfRQEm+ealbp0YDpwcAAAD0NxghieVqQ7irAyIj/ql1YQAAAAAA
+AAC7a45VJVDySI6NGUUj78V6BwAAAPQ3GCGJ5WpDuKsDIiP+qXViAAAAAAAAAE3A
+ZglVwXpEumGMlzfpwxUHAAAA9DcYIYnlakO4qwMiI/6pdWMAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAwAAAAFAAAAAAAAAAAAAAAAAAAAAAA=
+"/>
+<od:tableProperty name="DefaultView" type="2" value="2"/>
+<od:tableProperty name="DisplayViewsOnSharePointSite" type="2" value="1"/>
+<od:tableProperty name="TotalsRow" type="1" value="0"/>
+<od:tableProperty name="FilterOnLoad" type="1" value="0"/>
+<od:tableProperty name="OrderByOnLoad" type="1" value="1"/>
+<od:tableProperty name="HideNewField" type="1" value="0"/>
+<od:tableProperty name="BackTint" type="6" value="100"/>
+<od:tableProperty name="BackShade" type="6" value="100"/>
+<od:tableProperty name="ThemeFontIndex" type="4" value="1"/>
+<od:tableProperty name="AlternateBackThemeColorIndex" type="4" value="1"/>
+<od:tableProperty name="AlternateBackTint" type="6" value="100"/>
+<od:tableProperty name="AlternateBackShade" type="6" value="95"/>
+<od:tableProperty name="ReadOnlyWhenDisconnected" type="1" value="0"/>
+<od:tableProperty name="DatasheetGridlinesThemeColorIndex" type="4" value="3"/>
+<od:tableProperty name="DatasheetForeThemeColorIndex" type="4" value="0"/>
+<od:tableProperty name="PublishToWeb" type="2" value="1"/>
+</xsd:appinfo>
+</xsd:annotation>
+<xsd:complexType>
+<xsd:sequence>
+<xsd:element name="a" minOccurs="0" od:jetType="text" od:sqlSType="nvarchar">
+<xsd:annotation>
+<xsd:appinfo>
+<od:fieldProperty name="GUID" type="9" value="iZwMcYfRQEm+ealbp0YDpw==
+"/>
+<od:fieldProperty name="ColumnWidth" type="3" value="-1"/>
+<od:fieldProperty name="ColumnOrder" type="3" value="0"/>
+<od:fieldProperty name="ColumnHidden" type="1" value="0"/>
+<od:fieldProperty name="Required" type="1" value="0"/>
+<od:fieldProperty name="AllowZeroLength" type="1" value="1"/>
+<od:fieldProperty name="DisplayControl" type="3" value="109"/>
+<od:fieldProperty name="IMEMode" type="2" value="0"/>
+<od:fieldProperty name="IMESentenceMode" type="2" value="3"/>
+<od:fieldProperty name="UnicodeCompression" type="1" value="1"/>
+<od:fieldProperty name="TextAlign" type="2" value="0"/>
+<od:fieldProperty name="AggregateType" type="4" value="-1"/>
+<od:fieldProperty name="ResultType" type="2" value="0"/>
+<od:fieldProperty name="CurrencyLCID" type="4" value="0"/>
+</xsd:appinfo>
+</xsd:annotation>
+<xsd:simpleType>
+<xsd:restriction base="xsd:string">
+<xsd:maxLength value="255"/>
+</xsd:restriction>
+</xsd:simpleType>
+</xsd:element>
+<xsd:element name="b" minOccurs="0" od:jetType="text" od:sqlSType="nvarchar">
+<xsd:annotation>
+<xsd:appinfo>
+<od:fieldProperty name="GUID" type="9" value="u2uOVSVQ8kiOjRlFI+/Feg==
+"/>
+<od:fieldProperty name="ColumnWidth" type="3" value="-1"/>
+<od:fieldProperty name="ColumnOrder" type="3" value="0"/>
+<od:fieldProperty name="ColumnHidden" type="1" value="0"/>
+<od:fieldProperty name="Required" type="1" value="0"/>
+<od:fieldProperty name="AllowZeroLength" type="1" value="1"/>
+<od:fieldProperty name="DisplayControl" type="3" value="109"/>
+<od:fieldProperty name="IMEMode" type="2" value="0"/>
+<od:fieldProperty name="IMESentenceMode" type="2" value="3"/>
+<od:fieldProperty name="UnicodeCompression" type="1" value="1"/>
+<od:fieldProperty name="TextAlign" type="2" value="0"/>
+<od:fieldProperty name="AggregateType" type="4" value="-1"/>
+<od:fieldProperty name="ResultType" type="2" value="0"/>
+<od:fieldProperty name="CurrencyLCID" type="4" value="0"/>
+</xsd:appinfo>
+</xsd:annotation>
+<xsd:simpleType>
+<xsd:restriction base="xsd:string">
+<xsd:maxLength value="255"/>
+</xsd:restriction>
+</xsd:simpleType>
+</xsd:element>
+<xsd:element name="c" minOccurs="0" od:jetType="text" od:sqlSType="nvarchar">
+<xsd:annotation>
+<xsd:appinfo>
+<od:fieldProperty name="GUID" type="9" value="TcBmCVXBekS6YYyXN+nDFQ==
+"/>
+<od:fieldProperty name="ColumnWidth" type="3" value="-1"/>
+<od:fieldProperty name="ColumnOrder" type="3" value="0"/>
+<od:fieldProperty name="ColumnHidden" type="1" value="0"/>
+<od:fieldProperty name="Required" type="1" value="0"/>
+<od:fieldProperty name="AllowZeroLength" type="1" value="1"/>
+<od:fieldProperty name="DisplayControl" type="3" value="109"/>
+<od:fieldProperty name="IMEMode" type="2" value="0"/>
+<od:fieldProperty name="IMESentenceMode" type="2" value="3"/>
+<od:fieldProperty name="UnicodeCompression" type="1" value="1"/>
+<od:fieldProperty name="TextAlign" type="2" value="0"/>
+<od:fieldProperty name="AggregateType" type="4" value="-1"/>
+<od:fieldProperty name="ResultType" type="2" value="0"/>
+<od:fieldProperty name="CurrencyLCID" type="4" value="0"/>
+</xsd:appinfo>
+</xsd:annotation>
+<xsd:simpleType>
+<xsd:restriction base="xsd:string">
+<xsd:maxLength value="255"/>
+</xsd:restriction>
+</xsd:simpleType>
+</xsd:element>
+</xsd:sequence>
+</xsd:complexType>
+</xsd:element>
+</xsd:schema>
+<dataroot xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" generated="2018-03-29T09:47:28"/>
+</root>

二进制
test/test.zip