IDEFrame.py
changeset 814 5743cbdff669
child 819 4424918efe8b
equal deleted inserted replaced
813:1460273f40ed 814:5743cbdff669
       
     1 
       
     2 import os, sys
       
     3 import cPickle
       
     4 from types import TupleType
       
     5 
       
     6 import wx, wx.grid
       
     7 import wx.aui
       
     8 
       
     9 from editors.EditorPanel import EditorPanel
       
    10 from editors.SFCViewer import SFC_Viewer
       
    11 from editors.LDViewer import LD_Viewer
       
    12 from editors.TextViewer import TextViewer
       
    13 from editors.Viewer import Viewer, ZOOM_FACTORS
       
    14 from editors.GraphicViewer import GraphicViewer
       
    15 from editors.ResourceEditor import ConfigurationEditor, ResourceEditor
       
    16 from editors.DataTypeEditor import DataTypeEditor
       
    17 from PLCControler import *
       
    18 from controls import CustomTree, LibraryPanel, PouInstanceVariablesPanel, DebugVariablePanel, SearchResultPanel
       
    19 from dialogs import ProjectDialog, PouTransitionDialog, PouActionDialog, FindInPouDialog
       
    20 from util.BitmapLibrary import GetBitmap
       
    21 
       
    22 # Define PLCOpenEditor controls id
       
    23 [ID_PLCOPENEDITOR, ID_PLCOPENEDITORLEFTNOTEBOOK, 
       
    24  ID_PLCOPENEDITORBOTTOMNOTEBOOK, ID_PLCOPENEDITORRIGHTNOTEBOOK, 
       
    25  ID_PLCOPENEDITORPROJECTTREE, ID_PLCOPENEDITORMAINSPLITTER, 
       
    26  ID_PLCOPENEDITORSECONDSPLITTER, ID_PLCOPENEDITORTHIRDSPLITTER, 
       
    27  ID_PLCOPENEDITORLIBRARYPANEL, ID_PLCOPENEDITORLIBRARYSEARCHCTRL, 
       
    28  ID_PLCOPENEDITORLIBRARYTREE, ID_PLCOPENEDITORLIBRARYCOMMENT, 
       
    29  ID_PLCOPENEDITORTABSOPENED, ID_PLCOPENEDITORTABSOPENED, 
       
    30  ID_PLCOPENEDITOREDITORMENUTOOLBAR, ID_PLCOPENEDITOREDITORTOOLBAR, 
       
    31  ID_PLCOPENEDITORPROJECTPANEL, 
       
    32 ] = [wx.NewId() for _init_ctrls in range(17)]
       
    33 
       
    34 # Define PLCOpenEditor EditMenu extra items id
       
    35 [ID_PLCOPENEDITOREDITMENUENABLEUNDOREDO, ID_PLCOPENEDITOREDITMENUADDDATATYPE, 
       
    36  ID_PLCOPENEDITOREDITMENUADDFUNCTION, ID_PLCOPENEDITOREDITMENUADDFUNCTIONBLOCK, 
       
    37  ID_PLCOPENEDITOREDITMENUADDPROGRAM, ID_PLCOPENEDITOREDITMENUADDCONFIGURATION,
       
    38  ID_PLCOPENEDITOREDITMENUFINDNEXT, ID_PLCOPENEDITOREDITMENUFINDPREVIOUS,
       
    39  ID_PLCOPENEDITOREDITMENUSEARCHINPROJECT, 
       
    40 ] = [wx.NewId() for _init_coll_EditMenu_Items in range(9)]
       
    41 
       
    42 # Define PLCOpenEditor DisplayMenu extra items id
       
    43 [ID_PLCOPENEDITORDISPLAYMENURESETPERSPECTIVE, 
       
    44 ] = [wx.NewId() for _init_coll_DisplayMenu_Items in range(1)]
       
    45 
       
    46 #-------------------------------------------------------------------------------
       
    47 #                            EditorToolBar definitions
       
    48 #-------------------------------------------------------------------------------
       
    49 
       
    50 # Define PLCOpenEditor Toolbar items id
       
    51 [ID_PLCOPENEDITOREDITORTOOLBARSELECTION, ID_PLCOPENEDITOREDITORTOOLBARCOMMENT,
       
    52  ID_PLCOPENEDITOREDITORTOOLBARVARIABLE, ID_PLCOPENEDITOREDITORTOOLBARBLOCK,
       
    53  ID_PLCOPENEDITOREDITORTOOLBARCONNECTION, ID_PLCOPENEDITOREDITORTOOLBARWIRE,
       
    54  ID_PLCOPENEDITOREDITORTOOLBARPOWERRAIL, ID_PLCOPENEDITOREDITORTOOLBARRUNG,
       
    55  ID_PLCOPENEDITOREDITORTOOLBARCOIL, ID_PLCOPENEDITOREDITORTOOLBARCONTACT,
       
    56  ID_PLCOPENEDITOREDITORTOOLBARBRANCH, ID_PLCOPENEDITOREDITORTOOLBARINITIALSTEP,
       
    57  ID_PLCOPENEDITOREDITORTOOLBARSTEP, ID_PLCOPENEDITOREDITORTOOLBARTRANSITION,
       
    58  ID_PLCOPENEDITOREDITORTOOLBARACTIONBLOCK, ID_PLCOPENEDITOREDITORTOOLBARDIVERGENCE,
       
    59  ID_PLCOPENEDITOREDITORTOOLBARJUMP, ID_PLCOPENEDITOREDITORTOOLBARMOTION, 
       
    60 ] = [wx.NewId() for _init_coll_DefaultEditorToolBar_Items in range(18)]
       
    61 
       
    62 
       
    63 
       
    64 # Define behaviour of each Toolbar item according to current POU body type 
       
    65 # Informations meaning are in this order:
       
    66 #  - Item is toggled
       
    67 #  - PLCOpenEditor mode where item is displayed (could be more then one)
       
    68 #  - Item id
       
    69 #  - Item callback function name
       
    70 #  - Item icon filename
       
    71 #  - Item tooltip text
       
    72 EditorToolBarItems = {
       
    73     "FBD" : [(True, FREEDRAWING_MODE|DRIVENDRAWING_MODE,
       
    74               ID_PLCOPENEDITOREDITORTOOLBARMOTION, "OnMotionTool",
       
    75               "move", _("Move the view")),
       
    76              (True, FREEDRAWING_MODE|DRIVENDRAWING_MODE,
       
    77               ID_PLCOPENEDITOREDITORTOOLBARCOMMENT, "OnCommentTool",
       
    78               "add_comment", _("Create a new comment")),
       
    79              (True, FREEDRAWING_MODE|DRIVENDRAWING_MODE,
       
    80               ID_PLCOPENEDITOREDITORTOOLBARVARIABLE, "OnVariableTool",
       
    81               "add_variable", _("Create a new variable")),
       
    82              (True, FREEDRAWING_MODE|DRIVENDRAWING_MODE,
       
    83               ID_PLCOPENEDITOREDITORTOOLBARBLOCK, "OnBlockTool",
       
    84               "add_block", _("Create a new block")),
       
    85              (True, FREEDRAWING_MODE|DRIVENDRAWING_MODE, 
       
    86               ID_PLCOPENEDITOREDITORTOOLBARCONNECTION, "OnConnectionTool", 
       
    87               "add_connection", _("Create a new connection"))],
       
    88     "LD"  : [(True, FREEDRAWING_MODE|DRIVENDRAWING_MODE,
       
    89               ID_PLCOPENEDITOREDITORTOOLBARMOTION, "OnMotionTool",
       
    90               "move", _("Move the view")),
       
    91              (True, FREEDRAWING_MODE, 
       
    92               ID_PLCOPENEDITOREDITORTOOLBARCOMMENT, "OnCommentTool", 
       
    93               "add_comment", _("Create a new comment")),
       
    94              (True, FREEDRAWING_MODE, 
       
    95               ID_PLCOPENEDITOREDITORTOOLBARPOWERRAIL, "OnPowerRailTool", 
       
    96               "add_powerrail", _("Create a new power rail")),
       
    97              (False, DRIVENDRAWING_MODE, 
       
    98               ID_PLCOPENEDITOREDITORTOOLBARRUNG, "OnRungTool", 
       
    99               "add_rung", _("Create a new rung")),
       
   100              (True, FREEDRAWING_MODE, 
       
   101               ID_PLCOPENEDITOREDITORTOOLBARCOIL, "OnCoilTool", 
       
   102               "add_coil", _("Create a new coil")),
       
   103              (False, FREEDRAWING_MODE|DRIVENDRAWING_MODE, 
       
   104               ID_PLCOPENEDITOREDITORTOOLBARCONTACT, "OnContactTool", 
       
   105               "add_contact", _("Create a new contact")),
       
   106              (False, DRIVENDRAWING_MODE, 
       
   107               ID_PLCOPENEDITOREDITORTOOLBARBRANCH, "OnBranchTool", 
       
   108               "add_branch", _("Create a new branch")),
       
   109              (True, FREEDRAWING_MODE, 
       
   110               ID_PLCOPENEDITOREDITORTOOLBARVARIABLE, "OnVariableTool", 
       
   111               "add_variable", _("Create a new variable")),
       
   112              (False, FREEDRAWING_MODE|DRIVENDRAWING_MODE, 
       
   113               ID_PLCOPENEDITOREDITORTOOLBARBLOCK, "OnBlockTool", 
       
   114               "add_block", _("Create a new block")),
       
   115              (True, FREEDRAWING_MODE, 
       
   116               ID_PLCOPENEDITOREDITORTOOLBARCONNECTION, "OnConnectionTool", 
       
   117               "add_connection", _("Create a new connection"))],
       
   118     "SFC" : [(True, FREEDRAWING_MODE|DRIVENDRAWING_MODE,
       
   119               ID_PLCOPENEDITOREDITORTOOLBARMOTION, "OnMotionTool",
       
   120               "move", _("Move the view")),
       
   121              (True, FREEDRAWING_MODE|DRIVENDRAWING_MODE, 
       
   122               ID_PLCOPENEDITOREDITORTOOLBARCOMMENT, "OnCommentTool", 
       
   123               "add_comment", _("Create a new comment")),
       
   124              (True, FREEDRAWING_MODE|DRIVENDRAWING_MODE, 
       
   125               ID_PLCOPENEDITOREDITORTOOLBARINITIALSTEP, "OnInitialStepTool", 
       
   126               "add_initial_step", _("Create a new initial step")),
       
   127              (False, FREEDRAWING_MODE|DRIVENDRAWING_MODE, 
       
   128               ID_PLCOPENEDITOREDITORTOOLBARSTEP, "OnStepTool", 
       
   129               "add_step", _("Create a new step")),
       
   130              (True, FREEDRAWING_MODE, 
       
   131               ID_PLCOPENEDITOREDITORTOOLBARTRANSITION, "OnTransitionTool", 
       
   132               "add_transition", _("Create a new transition")),
       
   133              (False, FREEDRAWING_MODE|DRIVENDRAWING_MODE, 
       
   134               ID_PLCOPENEDITOREDITORTOOLBARACTIONBLOCK, "OnActionBlockTool", 
       
   135               "add_action", _("Create a new action block")),
       
   136              (False, FREEDRAWING_MODE|DRIVENDRAWING_MODE, 
       
   137               ID_PLCOPENEDITOREDITORTOOLBARDIVERGENCE, "OnDivergenceTool", 
       
   138               "add_divergence", _("Create a new divergence")),
       
   139              (False, FREEDRAWING_MODE|DRIVENDRAWING_MODE, 
       
   140               ID_PLCOPENEDITOREDITORTOOLBARJUMP, "OnJumpTool", 
       
   141               "add_jump", _("Create a new jump")),
       
   142              (True, FREEDRAWING_MODE, 
       
   143               ID_PLCOPENEDITOREDITORTOOLBARVARIABLE, "OnVariableTool", 
       
   144               "add_variable", _("Create a new variable")),
       
   145              (True, FREEDRAWING_MODE, 
       
   146               ID_PLCOPENEDITOREDITORTOOLBARBLOCK, "OnBlockTool", 
       
   147               "add_block", _("Create a new block")),
       
   148              (True, FREEDRAWING_MODE, 
       
   149               ID_PLCOPENEDITOREDITORTOOLBARCONNECTION, "OnConnectionTool", 
       
   150               "add_connection", _("Create a new connection")),
       
   151              (True, FREEDRAWING_MODE, 
       
   152               ID_PLCOPENEDITOREDITORTOOLBARPOWERRAIL, "OnPowerRailTool", 
       
   153               "add_powerrail", _("Create a new power rail")),
       
   154              (True, FREEDRAWING_MODE, 
       
   155               ID_PLCOPENEDITOREDITORTOOLBARCONTACT, "OnContactTool", 
       
   156               "add_contact", _("Create a new contact"))],
       
   157     "ST"  : [],
       
   158     "IL"  : [],
       
   159     "debug": [(True, FREEDRAWING_MODE|DRIVENDRAWING_MODE,
       
   160               ID_PLCOPENEDITOREDITORTOOLBARMOTION, "OnMotionTool",
       
   161               "move", _("Move the view"))],
       
   162 }
       
   163 
       
   164 #-------------------------------------------------------------------------------
       
   165 #                               Helper Functions
       
   166 #-------------------------------------------------------------------------------
       
   167 
       
   168 import base64
       
   169 
       
   170 def EncodeFileSystemPath(path, use_base64=True):
       
   171     path = path.encode(sys.getfilesystemencoding())
       
   172     if use_base64:
       
   173         return base64.encodestring(path)
       
   174     return path
       
   175 
       
   176 def DecodeFileSystemPath(path, is_base64=True):
       
   177     if is_base64:
       
   178         path = base64.decodestring(path)
       
   179     return unicode(path, sys.getfilesystemencoding())
       
   180 
       
   181 # Compatibility function for wx versions < 2.6
       
   182 def AppendMenu(parent, help, id, kind, text):
       
   183     if wx.VERSION >= (2, 6, 0):
       
   184         parent.Append(help=help, id=id, kind=kind, text=text)
       
   185     else:
       
   186         parent.Append(helpString=help, id=id, kind=kind, item=text)
       
   187 
       
   188 [TITLE, EDITORTOOLBAR, FILEMENU, EDITMENU, DISPLAYMENU, PROJECTTREE, 
       
   189  POUINSTANCEVARIABLESPANEL, LIBRARYTREE, SCALING, PAGETITLES
       
   190 ] = range(10)
       
   191 
       
   192 def GetShortcutKeyCallbackFunction(viewer_function):
       
   193     def ShortcutKeyFunction(self, event):
       
   194         control = self.FindFocus()
       
   195         if control is not None and control.GetName() in ["Viewer", "TextViewer"]:
       
   196             getattr(control.ParentWindow, viewer_function)()
       
   197         elif isinstance(control, wx.stc.StyledTextCtrl):
       
   198             getattr(control, viewer_function)()
       
   199         elif isinstance(control, wx.TextCtrl):
       
   200             control.ProcessEvent(event)
       
   201     return ShortcutKeyFunction
       
   202 
       
   203 def GetDeleteElementFunction(remove_function, parent_type=None, check_function=None):
       
   204     def DeleteElementFunction(self, selected):
       
   205         name = self.ProjectTree.GetItemText(selected)
       
   206         if check_function is None or not check_function(self.Controler, name):
       
   207             if parent_type is not None:
       
   208                 item_infos = self.ProjectTree.GetPyData(selected)
       
   209                 parent_name = item_infos["tagname"].split("::")[1]
       
   210                 remove_function(self.Controler, parent_name, name)
       
   211             else:
       
   212                 remove_function(self.Controler, name)
       
   213         else:
       
   214             self.ShowErrorMessage(_("\"%s\" is used by one or more POUs. It can't be removed!")%name)
       
   215     return DeleteElementFunction
       
   216 
       
   217 if wx.Platform == '__WXMSW__':
       
   218     TAB_BORDER = 6
       
   219     NOTEBOOK_BORDER = 6
       
   220 else:
       
   221     TAB_BORDER = 7
       
   222     NOTEBOOK_BORDER = 2
       
   223 
       
   224 def SimplifyTabLayout(tabs, rect):
       
   225     for tab in tabs:
       
   226         if tab["pos"][0] == rect.x:
       
   227             others = [t for t in tabs if t != tab]
       
   228             others.sort(lambda x,y: cmp(x["pos"][0], y["pos"][0]))
       
   229             for other in others:
       
   230                 if (other["pos"][1] == tab["pos"][1] and 
       
   231                     other["size"][1] == tab["size"][1] and
       
   232                     other["pos"][0] == tab["pos"][0] + tab["size"][0] + TAB_BORDER):
       
   233                     
       
   234                     tab["size"] = (tab["size"][0] + other["size"][0] + TAB_BORDER, tab["size"][1])
       
   235                     tab["pages"].extend(other["pages"])
       
   236                     tabs.remove(other)
       
   237                     
       
   238                     if tab["size"][0] == rect.width:
       
   239                         return True
       
   240                     
       
   241         elif tab["pos"][1] == rect.y:
       
   242             others = [t for t in tabs if t != tab]
       
   243             others.sort(lambda x,y: cmp(x["pos"][1], y["pos"][1]))
       
   244             for other in others:
       
   245                 if (other["pos"][0] == tab["pos"][0] and 
       
   246                     other["size"][0] == tab["size"][0] and
       
   247                     other["pos"][1] == tab["pos"][1] + tab["size"][1] + TAB_BORDER):
       
   248                     
       
   249                     tab["size"] = (tab["size"][0], tab["size"][1] + other["size"][1] + TAB_BORDER)
       
   250                     tab["pages"].extend(other["pages"])
       
   251                     tabs.remove(other)
       
   252                     
       
   253                     if tab["size"][1] == rect.height:
       
   254                         return True
       
   255     return False
       
   256     
       
   257 def ComputeTabsLayout(tabs, rect):
       
   258     if len(tabs) == 0:
       
   259         return tabs
       
   260     if len(tabs) == 1:
       
   261         return tabs[0]
       
   262     split = None
       
   263     for idx, tab in enumerate(tabs):
       
   264         if len(tab["pages"]) == 0:
       
   265             raise ValueError, "Not possible"
       
   266         if tab["size"][0] == rect.width:
       
   267             if tab["pos"][1] == rect.y:
       
   268                 split = (wx.TOP, float(tab["size"][1]) / float(rect.height))
       
   269                 split_rect = wx.Rect(rect.x, rect.y + tab["size"][1] + TAB_BORDER, 
       
   270                                      rect.width, rect.height - tab["size"][1] - TAB_BORDER)
       
   271             elif tab["pos"][1] == rect.height + 1 - tab["size"][1]:
       
   272                 split = (wx.BOTTOM, 1.0 - float(tab["size"][1]) / float(rect.height))
       
   273                 split_rect = wx.Rect(rect.x, rect.y, 
       
   274                                      rect.width, rect.height - tab["size"][1] - TAB_BORDER)
       
   275             break
       
   276         elif tab["size"][1] == rect.height:
       
   277             if tab["pos"][0] == rect.x:
       
   278                 split = (wx.LEFT, float(tab["size"][0]) / float(rect.width))
       
   279                 split_rect = wx.Rect(rect.x + tab["size"][0] + TAB_BORDER, rect.y, 
       
   280                                      rect.width - tab["size"][0] - TAB_BORDER, rect.height)
       
   281             elif tab["pos"][0] == rect.width + 1 - tab["size"][0]:
       
   282                 split = (wx.RIGHT, 1.0 - float(tab["size"][0]) / float(rect.width))
       
   283                 split_rect = wx.Rect(rect.x, rect.y, 
       
   284                                      rect.width - tab["size"][0] - TAB_BORDER, rect.height)
       
   285             break
       
   286     if split != None:
       
   287         split_tab = tabs.pop(idx)
       
   288         return {"split": split,
       
   289                 "tab": split_tab, 
       
   290                 "others": ComputeTabsLayout(tabs, split_rect)}
       
   291     else:
       
   292         if SimplifyTabLayout(tabs, rect):
       
   293             return ComputeTabsLayout(tabs, rect)
       
   294     return tabs
       
   295 
       
   296 #-------------------------------------------------------------------------------
       
   297 #                              IDEFrame Base Class
       
   298 #-------------------------------------------------------------------------------
       
   299 
       
   300 UNEDITABLE_NAMES_DICT = dict([(_(name), name) for name in UNEDITABLE_NAMES])
       
   301 
       
   302 class IDEFrame(wx.Frame):
       
   303     
       
   304     Starting = False
       
   305     
       
   306     # Compatibility function for wx versions < 2.6
       
   307     if wx.VERSION < (2, 6, 0):
       
   308         def Bind(self, event, function, id = None):
       
   309             if id is not None:
       
   310                 event(self, id, function)
       
   311             else:
       
   312                 event(self, function)
       
   313     
       
   314     def _init_coll_MenuBar_Menus(self, parent):
       
   315         parent.Append(menu=self.FileMenu, title=_(u'&File'))
       
   316         parent.Append(menu=self.EditMenu, title=_(u'&Edit'))
       
   317         parent.Append(menu=self.DisplayMenu, title=_(u'&Display'))
       
   318         parent.Append(menu=self.HelpMenu, title=_(u'&Help'))
       
   319 
       
   320     def _init_coll_FileMenu_Items(self, parent):
       
   321         pass
       
   322     
       
   323     def _init_coll_AddMenu_Items(self, parent, add_config=True):
       
   324         AppendMenu(parent, help='', id=ID_PLCOPENEDITOREDITMENUADDDATATYPE,
       
   325               kind=wx.ITEM_NORMAL, text=_(u'&Data Type'))
       
   326         AppendMenu(parent, help='', id=ID_PLCOPENEDITOREDITMENUADDFUNCTION,
       
   327               kind=wx.ITEM_NORMAL, text=_(u'&Function'))
       
   328         AppendMenu(parent, help='', id=ID_PLCOPENEDITOREDITMENUADDFUNCTIONBLOCK,
       
   329               kind=wx.ITEM_NORMAL, text=_(u'Function &Block'))
       
   330         AppendMenu(parent, help='', id=ID_PLCOPENEDITOREDITMENUADDPROGRAM,
       
   331               kind=wx.ITEM_NORMAL, text=_(u'&Program'))
       
   332         if add_config:
       
   333             AppendMenu(parent, help='', id=ID_PLCOPENEDITOREDITMENUADDCONFIGURATION,
       
   334                   kind=wx.ITEM_NORMAL, text=_(u'&Configuration'))
       
   335     
       
   336     def _init_coll_EditMenu_Items(self, parent):
       
   337         AppendMenu(parent, help='', id=wx.ID_UNDO,
       
   338               kind=wx.ITEM_NORMAL, text=_(u'Undo') + '\tCTRL+Z')
       
   339         AppendMenu(parent, help='', id=wx.ID_REDO,
       
   340               kind=wx.ITEM_NORMAL, text=_(u'Redo') + '\tCTRL+Y')
       
   341         #AppendMenu(parent, help='', id=ID_PLCOPENEDITOREDITMENUENABLEUNDOREDO,
       
   342         #      kind=wx.ITEM_CHECK, text=_(u'Enable Undo/Redo'))
       
   343         enable_undo_redo = _(u'Enable Undo/Redo') # Keeping text in translations for possible menu reactivation
       
   344         parent.AppendSeparator()
       
   345         AppendMenu(parent, help='', id=wx.ID_CUT,
       
   346               kind=wx.ITEM_NORMAL, text=_(u'Cut') + '\tCTRL+X')
       
   347         AppendMenu(parent, help='', id=wx.ID_COPY,
       
   348               kind=wx.ITEM_NORMAL, text=_(u'Copy') + '\tCTRL+C')
       
   349         AppendMenu(parent, help='', id=wx.ID_PASTE,
       
   350               kind=wx.ITEM_NORMAL, text=_(u'Paste') + '\tCTRL+V')
       
   351         parent.AppendSeparator()
       
   352         AppendMenu(parent, help='', id=wx.ID_FIND,
       
   353               kind=wx.ITEM_NORMAL, text=_(u'Find') + '\tCTRL+F')
       
   354         AppendMenu(parent, help='', id=ID_PLCOPENEDITOREDITMENUFINDNEXT,
       
   355               kind=wx.ITEM_NORMAL, text=_(u'Find Next') + '\tCTRL+K')
       
   356         AppendMenu(parent, help='', id=ID_PLCOPENEDITOREDITMENUFINDPREVIOUS,
       
   357               kind=wx.ITEM_NORMAL, text=_(u'Find Previous') + '\tCTRL+SHIFT+K')
       
   358         parent.AppendSeparator()
       
   359         AppendMenu(parent, help='', id=ID_PLCOPENEDITOREDITMENUSEARCHINPROJECT,
       
   360               kind=wx.ITEM_NORMAL, text=_(u'Search in Project') + '\tCTRL+SHIFT+F')
       
   361         parent.AppendSeparator()
       
   362         add_menu = wx.Menu(title='')
       
   363         self._init_coll_AddMenu_Items(add_menu)
       
   364         parent.AppendMenu(wx.ID_ADD, _(u"&Add Element"), add_menu)
       
   365         AppendMenu(parent, help='', id=wx.ID_SELECTALL,
       
   366               kind=wx.ITEM_NORMAL, text=_(u'Select All') + '\tCTRL+A')
       
   367         AppendMenu(parent, help='', id=wx.ID_DELETE,
       
   368               kind=wx.ITEM_NORMAL, text=_(u'&Delete'))
       
   369         self.Bind(wx.EVT_MENU, self.OnUndoMenu, id=wx.ID_UNDO)
       
   370         self.Bind(wx.EVT_MENU, self.OnRedoMenu, id=wx.ID_REDO)
       
   371         #self.Bind(wx.EVT_MENU, self.OnEnableUndoRedoMenu, id=ID_PLCOPENEDITOREDITMENUENABLEUNDOREDO)
       
   372         self.Bind(wx.EVT_MENU, self.OnCutMenu, id=wx.ID_CUT)
       
   373         self.Bind(wx.EVT_MENU, self.OnCopyMenu, id=wx.ID_COPY)
       
   374         self.Bind(wx.EVT_MENU, self.OnPasteMenu, id=wx.ID_PASTE)
       
   375         self.Bind(wx.EVT_MENU, self.OnFindMenu, id=wx.ID_FIND)
       
   376         self.Bind(wx.EVT_MENU, self.OnFindNextMenu, 
       
   377               id=ID_PLCOPENEDITOREDITMENUFINDNEXT)
       
   378         self.Bind(wx.EVT_MENU, self.OnFindPreviousMenu, 
       
   379               id=ID_PLCOPENEDITOREDITMENUFINDPREVIOUS)
       
   380         self.Bind(wx.EVT_MENU, self.OnSearchInProjectMenu, 
       
   381               id=ID_PLCOPENEDITOREDITMENUSEARCHINPROJECT)
       
   382         self.Bind(wx.EVT_MENU, self.OnSearchInProjectMenu, 
       
   383               id=ID_PLCOPENEDITOREDITMENUSEARCHINPROJECT)
       
   384         self.Bind(wx.EVT_MENU, self.OnAddDataTypeMenu,
       
   385               id=ID_PLCOPENEDITOREDITMENUADDDATATYPE)
       
   386         self.Bind(wx.EVT_MENU, self.GenerateAddPouFunction("function"),
       
   387               id=ID_PLCOPENEDITOREDITMENUADDFUNCTION)
       
   388         self.Bind(wx.EVT_MENU, self.GenerateAddPouFunction("functionBlock"),
       
   389               id=ID_PLCOPENEDITOREDITMENUADDFUNCTIONBLOCK)
       
   390         self.Bind(wx.EVT_MENU, self.GenerateAddPouFunction("program"),
       
   391               id=ID_PLCOPENEDITOREDITMENUADDPROGRAM)
       
   392         self.Bind(wx.EVT_MENU, self.OnAddConfigurationMenu,
       
   393               id=ID_PLCOPENEDITOREDITMENUADDCONFIGURATION)
       
   394         self.Bind(wx.EVT_MENU, self.OnSelectAllMenu, id=wx.ID_SELECTALL)
       
   395         self.Bind(wx.EVT_MENU, self.OnDeleteMenu, id=wx.ID_DELETE)
       
   396         
       
   397         self.AddToMenuToolBar([(wx.ID_UNDO, "undo", _(u'Undo'), None),
       
   398                                (wx.ID_REDO, "redo", _(u'Redo'), None),
       
   399                                None,
       
   400                                (wx.ID_CUT, "cut", _(u'Cut'), None),
       
   401                                (wx.ID_COPY, "copy", _(u'Copy'), None),
       
   402                                (wx.ID_PASTE, "paste", _(u'Paste'), None),
       
   403                                None,
       
   404                                (ID_PLCOPENEDITOREDITMENUSEARCHINPROJECT, "find", _(u'Search in Project'), None)])
       
   405 
       
   406     def _init_coll_DisplayMenu_Items(self, parent):
       
   407         AppendMenu(parent, help='', id=wx.ID_REFRESH,
       
   408               kind=wx.ITEM_NORMAL, text=_(u'Refresh') + '\tCTRL+R')
       
   409         if self.EnableDebug:
       
   410             AppendMenu(parent, help='', id=wx.ID_CLEAR,
       
   411                   kind=wx.ITEM_NORMAL, text=_(u'Clear Errors') + '\tCTRL+K')
       
   412         parent.AppendSeparator()
       
   413         zoommenu = wx.Menu(title='')
       
   414         parent.AppendMenu(wx.ID_ZOOM_FIT, _("Zoom"), zoommenu)
       
   415         for idx, value in enumerate(ZOOM_FACTORS):
       
   416             new_id = wx.NewId()
       
   417             AppendMenu(zoommenu, help='', id=new_id,
       
   418                   kind=wx.ITEM_RADIO, text=str(int(round(value * 100))) + "%")
       
   419             self.Bind(wx.EVT_MENU, self.GenerateZoomFunction(idx), id=new_id)
       
   420         
       
   421         parent.AppendSeparator()
       
   422         AppendMenu(parent, help='', id=ID_PLCOPENEDITORDISPLAYMENURESETPERSPECTIVE,
       
   423               kind=wx.ITEM_NORMAL, text=_(u'Reset Perspective'))
       
   424         self.Bind(wx.EVT_MENU, self.OnResetPerspective, id=ID_PLCOPENEDITORDISPLAYMENURESETPERSPECTIVE)
       
   425         
       
   426         self.Bind(wx.EVT_MENU, self.OnRefreshMenu, id=wx.ID_REFRESH)
       
   427         if self.EnableDebug:
       
   428             self.Bind(wx.EVT_MENU, self.OnClearErrorsMenu, id=wx.ID_CLEAR)
       
   429             
       
   430     def _init_coll_HelpMenu_Items(self, parent):
       
   431         pass
       
   432 
       
   433     def _init_utils(self):
       
   434         self.MenuBar = wx.MenuBar()
       
   435 
       
   436         self.FileMenu = wx.Menu(title='')
       
   437         self.EditMenu = wx.Menu(title='')
       
   438         self.DisplayMenu = wx.Menu(title='')
       
   439         self.HelpMenu = wx.Menu(title='')
       
   440         
       
   441         self._init_coll_MenuBar_Menus(self.MenuBar)
       
   442         self._init_coll_FileMenu_Items(self.FileMenu)
       
   443         self._init_coll_EditMenu_Items(self.EditMenu)
       
   444         self._init_coll_DisplayMenu_Items(self.DisplayMenu)
       
   445         self._init_coll_HelpMenu_Items(self.HelpMenu)
       
   446 
       
   447     def _init_ctrls(self, prnt):
       
   448         wx.Frame.__init__(self, id=ID_PLCOPENEDITOR, name='IDEFrame',
       
   449               parent=prnt, pos=wx.DefaultPosition, size=wx.Size(1000, 600),
       
   450               style=wx.DEFAULT_FRAME_STYLE)
       
   451         self.SetClientSize(wx.Size(1000, 600))
       
   452         self.Bind(wx.EVT_ACTIVATE, self.OnActivated)
       
   453         self.Bind(wx.EVT_SIZE, self.OnResize)
       
   454         
       
   455         self.TabsImageList = wx.ImageList(31, 16)
       
   456         self.TabsImageListIndexes = {}
       
   457         
       
   458         #-----------------------------------------------------------------------
       
   459         #                          Creating main structure
       
   460         #-----------------------------------------------------------------------
       
   461         
       
   462         self.AUIManager = wx.aui.AuiManager(self)
       
   463         self.AUIManager.SetDockSizeConstraint(0.5, 0.5)
       
   464         self.Panes = {}
       
   465         
       
   466         self.LeftNoteBook = wx.aui.AuiNotebook(self, ID_PLCOPENEDITORLEFTNOTEBOOK,
       
   467               style=wx.aui.AUI_NB_TOP|wx.aui.AUI_NB_TAB_SPLIT|wx.aui.AUI_NB_TAB_MOVE|
       
   468                     wx.aui.AUI_NB_SCROLL_BUTTONS|wx.aui.AUI_NB_TAB_EXTERNAL_MOVE)
       
   469         self.LeftNoteBook.Bind(wx.aui.EVT_AUINOTEBOOK_ALLOW_DND, 
       
   470                 self.OnAllowNotebookDnD)
       
   471         self.AUIManager.AddPane(self.LeftNoteBook, 
       
   472               wx.aui.AuiPaneInfo().Name("ProjectPane").
       
   473               Left().Layer(1).
       
   474               BestSize(wx.Size(300, 500)).CloseButton(False))
       
   475         
       
   476         self.BottomNoteBook = wx.aui.AuiNotebook(self, ID_PLCOPENEDITORBOTTOMNOTEBOOK,
       
   477               style=wx.aui.AUI_NB_TOP|wx.aui.AUI_NB_TAB_SPLIT|wx.aui.AUI_NB_TAB_MOVE|
       
   478                     wx.aui.AUI_NB_SCROLL_BUTTONS|wx.aui.AUI_NB_TAB_EXTERNAL_MOVE)
       
   479         self.BottomNoteBook.Bind(wx.aui.EVT_AUINOTEBOOK_ALLOW_DND, 
       
   480                 self.OnAllowNotebookDnD)
       
   481         self.AUIManager.AddPane(self.BottomNoteBook, 
       
   482               wx.aui.AuiPaneInfo().Name("ResultPane").
       
   483               Bottom().Layer(0).
       
   484               BestSize(wx.Size(800, 300)).CloseButton(False))
       
   485         
       
   486         self.RightNoteBook = wx.aui.AuiNotebook(self, ID_PLCOPENEDITORRIGHTNOTEBOOK,
       
   487               style=wx.aui.AUI_NB_TOP|wx.aui.AUI_NB_TAB_SPLIT|wx.aui.AUI_NB_TAB_MOVE|
       
   488                     wx.aui.AUI_NB_SCROLL_BUTTONS|wx.aui.AUI_NB_TAB_EXTERNAL_MOVE)
       
   489         self.RightNoteBook.Bind(wx.aui.EVT_AUINOTEBOOK_ALLOW_DND, 
       
   490                 self.OnAllowNotebookDnD)
       
   491         self.AUIManager.AddPane(self.RightNoteBook, 
       
   492               wx.aui.AuiPaneInfo().Name("LibraryPane").
       
   493               Right().Layer(0).
       
   494               BestSize(wx.Size(250, 400)).CloseButton(False))
       
   495         
       
   496         self.TabsOpened = wx.aui.AuiNotebook(self, ID_PLCOPENEDITORTABSOPENED, 
       
   497               style=wx.aui.AUI_NB_DEFAULT_STYLE|wx.aui.AUI_NB_WINDOWLIST_BUTTON)
       
   498         self.TabsOpened.Bind(wx.aui.EVT_AUINOTEBOOK_PAGE_CHANGING,
       
   499               self.OnPouSelectedChanging)
       
   500         self.TabsOpened.Bind(wx.aui.EVT_AUINOTEBOOK_PAGE_CHANGED,
       
   501               self.OnPouSelectedChanged)
       
   502         self.TabsOpened.Bind(wx.aui.EVT_AUINOTEBOOK_PAGE_CLOSE,
       
   503               self.OnPageClose)
       
   504         self.TabsOpened.Bind(wx.aui.EVT_AUINOTEBOOK_END_DRAG,
       
   505               self.OnPageDragged)
       
   506         self.AUIManager.AddPane(self.TabsOpened, 
       
   507               wx.aui.AuiPaneInfo().CentrePane().Name("TabsPane"))
       
   508         
       
   509         #-----------------------------------------------------------------------
       
   510         #                    Creating PLCopen Project Types Tree
       
   511         #-----------------------------------------------------------------------
       
   512         
       
   513         self.MainTabs = {}
       
   514         
       
   515         self.ProjectPanel = wx.SplitterWindow(id=ID_PLCOPENEDITORPROJECTPANEL,
       
   516                   name='ProjectPanel', parent=self.LeftNoteBook, point=wx.Point(0, 0),
       
   517                   size=wx.Size(0, 0), style=wx.SP_3D)
       
   518         
       
   519         self.ProjectTree = CustomTree(id=ID_PLCOPENEDITORPROJECTTREE,
       
   520                   name='ProjectTree', parent=self.ProjectPanel, 
       
   521                   pos=wx.Point(0, 0), size=wx.Size(0, 0),
       
   522                   style=wx.TR_HAS_BUTTONS|wx.TR_SINGLE|wx.SUNKEN_BORDER|wx.TR_EDIT_LABELS)
       
   523         self.ProjectTree.SetBackgroundBitmap(GetBitmap("custom_tree_background"),
       
   524                                              wx.ALIGN_RIGHT|wx.ALIGN_BOTTOM)
       
   525         add_menu = wx.Menu()
       
   526         self._init_coll_AddMenu_Items(add_menu)
       
   527         self.ProjectTree.SetAddMenu(add_menu)
       
   528         if wx.Platform == '__WXMSW__':
       
   529             self.Bind(wx.EVT_TREE_ITEM_RIGHT_CLICK, self.OnProjectTreeRightUp,
       
   530                   id=ID_PLCOPENEDITORPROJECTTREE)
       
   531             self.Bind(wx.EVT_TREE_SEL_CHANGED, self.OnProjectTreeItemSelected,
       
   532                   id=ID_PLCOPENEDITORPROJECTTREE)
       
   533         else:
       
   534             self.ProjectTree.Bind(wx.EVT_RIGHT_UP, self.OnProjectTreeRightUp)
       
   535             self.ProjectTree.Bind(wx.EVT_LEFT_UP, self.OnProjectTreeLeftUp)
       
   536             self.Bind(wx.EVT_TREE_SEL_CHANGING, self.OnProjectTreeItemChanging,
       
   537                   id=ID_PLCOPENEDITORPROJECTTREE)
       
   538         self.Bind(wx.EVT_TREE_BEGIN_DRAG, self.OnProjectTreeBeginDrag,
       
   539               id=ID_PLCOPENEDITORPROJECTTREE)
       
   540         self.Bind(wx.EVT_TREE_BEGIN_LABEL_EDIT, self.OnProjectTreeItemBeginEdit,
       
   541               id=ID_PLCOPENEDITORPROJECTTREE)
       
   542         self.Bind(wx.EVT_TREE_END_LABEL_EDIT, self.OnProjectTreeItemEndEdit,
       
   543               id=ID_PLCOPENEDITORPROJECTTREE)
       
   544         self.Bind(wx.EVT_TREE_ITEM_ACTIVATED, self.OnProjectTreeItemActivated,
       
   545               id=ID_PLCOPENEDITORPROJECTTREE)
       
   546         
       
   547         #-----------------------------------------------------------------------
       
   548         #        Creating PLCopen Project POU Instance Variables Panel
       
   549         #-----------------------------------------------------------------------
       
   550         
       
   551         self.PouInstanceVariablesPanel = PouInstanceVariablesPanel(self.ProjectPanel, self, self.Controler, self.EnableDebug)
       
   552         
       
   553         self.MainTabs["ProjectPanel"] = (self.ProjectPanel, _("Project"))
       
   554         self.LeftNoteBook.AddPage(*self.MainTabs["ProjectPanel"])
       
   555         
       
   556         self.ProjectPanel.SplitHorizontally(self.ProjectTree, self.PouInstanceVariablesPanel, 300)
       
   557         
       
   558         #-----------------------------------------------------------------------
       
   559         #                            Creating Tool Bar
       
   560         #-----------------------------------------------------------------------
       
   561         
       
   562         MenuToolBar = wx.ToolBar(self, ID_PLCOPENEDITOREDITORMENUTOOLBAR, wx.DefaultPosition, wx.DefaultSize,
       
   563                 wx.TB_FLAT | wx.TB_NODIVIDER | wx.NO_BORDER)
       
   564         MenuToolBar.SetToolBitmapSize(wx.Size(25, 25))
       
   565         MenuToolBar.Realize()
       
   566         self.Panes["MenuToolBar"] = MenuToolBar
       
   567         self.AUIManager.AddPane(MenuToolBar, wx.aui.AuiPaneInfo().
       
   568                   Name("MenuToolBar").Caption(_("Menu ToolBar")).
       
   569                   ToolbarPane().Top().
       
   570                   LeftDockable(False).RightDockable(False))
       
   571         
       
   572         EditorToolBar = wx.ToolBar(self, ID_PLCOPENEDITOREDITORTOOLBAR, wx.DefaultPosition, wx.DefaultSize,
       
   573                 wx.TB_FLAT | wx.TB_NODIVIDER | wx.NO_BORDER)
       
   574         EditorToolBar.SetToolBitmapSize(wx.Size(25, 25))
       
   575         EditorToolBar.AddRadioTool(ID_PLCOPENEDITOREDITORTOOLBARSELECTION, 
       
   576               GetBitmap("select"), wx.NullBitmap, _("Select an object"))
       
   577         EditorToolBar.Realize()
       
   578         self.Panes["EditorToolBar"] = EditorToolBar
       
   579         self.AUIManager.AddPane(EditorToolBar, wx.aui.AuiPaneInfo().
       
   580                   Name("EditorToolBar").Caption(_("Editor ToolBar")).
       
   581                   ToolbarPane().Top().Position(1).
       
   582                   LeftDockable(False).RightDockable(False))
       
   583             
       
   584         self.Bind(wx.EVT_MENU, self.OnSelectionTool, 
       
   585               id=ID_PLCOPENEDITOREDITORTOOLBARSELECTION)
       
   586         
       
   587         #-----------------------------------------------------------------------
       
   588         #                            Creating Search Panel
       
   589         #-----------------------------------------------------------------------
       
   590         
       
   591         self.SearchResultPanel = SearchResultPanel(self.BottomNoteBook, self)
       
   592         self.MainTabs["SearchResultPanel"] = (self.SearchResultPanel, _("Search"))
       
   593         self.BottomNoteBook.AddPage(*self.MainTabs["SearchResultPanel"])
       
   594         
       
   595         #-----------------------------------------------------------------------
       
   596         #                            Creating Library Panel
       
   597         #-----------------------------------------------------------------------
       
   598         
       
   599         self.LibraryPanel = LibraryPanel(self, True)
       
   600         self.MainTabs["LibraryPanel"] = (self.LibraryPanel, _("Library"))
       
   601         self.RightNoteBook.AddPage(*self.MainTabs["LibraryPanel"])
       
   602                 
       
   603         self._init_utils()
       
   604         self.SetMenuBar(self.MenuBar)
       
   605                 
       
   606         if self.EnableDebug:
       
   607             self.DebugVariablePanel = DebugVariablePanel(self.RightNoteBook, self.Controler)
       
   608             self.MainTabs["DebugVariablePanel"] = (self.DebugVariablePanel, _("Debugger"))
       
   609             self.RightNoteBook.AddPage(*self.MainTabs["DebugVariablePanel"])
       
   610         
       
   611         self.AUIManager.Update()
       
   612     
       
   613         self.FindDialog = FindInPouDialog(self)
       
   614         self.FindDialog.Hide()
       
   615     
       
   616     ## Constructor of the PLCOpenEditor class.
       
   617     #  @param parent The parent window.
       
   618     #  @param controler The controler been used by PLCOpenEditor (default: None).
       
   619     #  @param fileOpen The filepath to open if no controler defined (default: None).
       
   620     #  @param debug The filepath to open if no controler defined (default: False).
       
   621     def __init__(self, parent, enable_debug = False):
       
   622         self.Controler = None
       
   623         self.Config = wx.ConfigBase.Get()
       
   624         self.EnableDebug = enable_debug
       
   625         
       
   626         self._init_ctrls(parent)
       
   627         
       
   628         # Define Tree item icon list
       
   629         self.TreeImageList = wx.ImageList(16, 16)
       
   630         self.TreeImageDict = {}
       
   631         
       
   632         # Icons for languages
       
   633         for language in LANGUAGES:
       
   634             self.TreeImageDict[language] = self.TreeImageList.Add(GetBitmap(language))
       
   635             
       
   636         # Icons for other items
       
   637         for imgname, itemtype in [
       
   638             #editables
       
   639             ("PROJECT",        ITEM_PROJECT),
       
   640             #("POU",            ITEM_POU),
       
   641             #("VARIABLE",       ITEM_VARIABLE),
       
   642             ("TRANSITION",     ITEM_TRANSITION),
       
   643             ("ACTION",         ITEM_ACTION),
       
   644             ("CONFIGURATION",  ITEM_CONFIGURATION),
       
   645             ("RESOURCE",       ITEM_RESOURCE),
       
   646             ("DATATYPE",       ITEM_DATATYPE),
       
   647             # uneditables
       
   648             ("DATATYPES",      ITEM_DATATYPES),
       
   649             ("FUNCTION",       ITEM_FUNCTION),
       
   650             ("FUNCTIONBLOCK",  ITEM_FUNCTIONBLOCK),
       
   651             ("PROGRAM",        ITEM_PROGRAM),
       
   652             ("VAR_LOCAL",      ITEM_VAR_LOCAL),
       
   653             ("VAR_LOCAL",      ITEM_VAR_GLOBAL),
       
   654             ("VAR_LOCAL",      ITEM_VAR_EXTERNAL),
       
   655             ("VAR_LOCAL",      ITEM_VAR_TEMP),
       
   656             ("VAR_INPUT",      ITEM_VAR_INPUT),
       
   657             ("VAR_OUTPUT",     ITEM_VAR_OUTPUT),
       
   658             ("VAR_INOUT",      ITEM_VAR_INOUT),
       
   659             ("TRANSITIONS",    ITEM_TRANSITIONS),
       
   660             ("ACTIONS",        ITEM_ACTIONS),
       
   661             ("CONFIGURATIONS", ITEM_CONFIGURATIONS),
       
   662             ("RESOURCES",      ITEM_RESOURCES),
       
   663             ("PROPERTIES",     ITEM_PROPERTIES)]:
       
   664             self.TreeImageDict[itemtype] = self.TreeImageList.Add(GetBitmap(imgname))
       
   665         
       
   666         # Assign icon list to TreeCtrls
       
   667         self.ProjectTree.SetImageList(self.TreeImageList)
       
   668         self.PouInstanceVariablesPanel.SetTreeImageList(self.TreeImageList)
       
   669         
       
   670         self.CurrentEditorToolBar = []
       
   671         self.CurrentMenu = None
       
   672         self.SelectedItem = None
       
   673         self.SearchParams = None
       
   674         self.Highlights = {}
       
   675         self.DrawingMode = FREEDRAWING_MODE
       
   676         #self.DrawingMode = DRIVENDRAWING_MODE
       
   677         self.AuiTabCtrl = []
       
   678         self.DefaultPerspective = None
       
   679         
       
   680         # Initialize Printing configuring elements
       
   681         self.PrintData = wx.PrintData()
       
   682         self.PrintData.SetPaperId(wx.PAPER_A4)
       
   683         self.PrintData.SetPrintMode(wx.PRINT_MODE_PRINTER)
       
   684         self.PageSetupData = wx.PageSetupDialogData(self.PrintData)
       
   685         self.PageSetupData.SetMarginTopLeft(wx.Point(10, 15))
       
   686         self.PageSetupData.SetMarginBottomRight(wx.Point(10, 20))
       
   687         
       
   688         self.SetRefreshFunctions()
       
   689     
       
   690     def __del__(self):
       
   691         self.FindDialog.Destroy()
       
   692     
       
   693     def ResetStarting(self):
       
   694         self.Starting = False
       
   695     
       
   696     def Show(self):
       
   697         wx.Frame.Show(self)
       
   698         wx.CallAfter(self.RestoreLastState)
       
   699     
       
   700     def OnActivated(self, event):
       
   701         if event.GetActive():
       
   702             wx.CallAfter(self._Refresh, TITLE, EDITORTOOLBAR, FILEMENU, EDITMENU, DISPLAYMENU)
       
   703         event.Skip()
       
   704 
       
   705 #-------------------------------------------------------------------------------
       
   706 #                Saving and restoring frame organization functions
       
   707 #-------------------------------------------------------------------------------
       
   708 
       
   709     def OnResize(self, event):
       
   710         if self.Starting:
       
   711             self.RestoreLastLayout()
       
   712             if wx.Platform == '__WXMSW__':
       
   713                 wx.CallAfter(self.ResetStarting)
       
   714             else:
       
   715                 self.ResetStarting()
       
   716             wx.CallAfter(self.RefreshEditor)
       
   717         event.Skip()
       
   718     
       
   719     def GetProjectConfiguration(self):
       
   720         projects = {}
       
   721         try:
       
   722             if self.Config.HasEntry("projects"):
       
   723                 projects = cPickle.loads(str(self.Config.Read("projects")))
       
   724         except:
       
   725             pass
       
   726         
       
   727         return projects.get(
       
   728             EncodeFileSystemPath(os.path.realpath(self.Controler.GetFilePath())), {})
       
   729     
       
   730     def SavePageState(self, page):
       
   731         state = page.GetState()
       
   732         if state is not None:
       
   733             if self.Config.HasEntry("projects"):
       
   734                 projects = cPickle.loads(str(self.Config.Read("projects")))
       
   735             else:
       
   736                 projects = {}
       
   737             
       
   738             project_infos = projects.setdefault(
       
   739                  EncodeFileSystemPath(os.path.realpath(self.Controler.GetFilePath())), {})
       
   740             editors_state = project_infos.setdefault("editors_state", {})
       
   741             
       
   742             if page.IsDebugging():
       
   743                 editors_state[page.GetInstancePath()] = state
       
   744             else:
       
   745                 editors_state[page.GetTagName()] = state
       
   746             
       
   747             self.Config.Write("projects", cPickle.dumps(projects))
       
   748             self.Config.Flush()
       
   749     
       
   750     def GetTabInfos(self, tab):
       
   751         if isinstance(tab, EditorPanel):
       
   752             if tab.IsDebugging():
       
   753                 return ("debug", tab.GetInstancePath())
       
   754             else:
       
   755                 return ("editor", tab.GetTagName())
       
   756         else:
       
   757             for page_name, (page_ref, page_title) in self.MainTabs.iteritems():
       
   758                 if page_ref == tab:
       
   759                     return ("main", page_name)
       
   760         return None
       
   761     
       
   762     def SaveTabLayout(self, notebook):
       
   763         tabs = []
       
   764         for child in notebook.GetChildren():
       
   765             if isinstance(child, wx.aui.AuiTabCtrl):
       
   766                 if child.GetPageCount() > 0:
       
   767                     pos = child.GetPosition()
       
   768                     tab = {"pos": (pos.x, pos.y), "pages": []}
       
   769                     tab_size = child.GetSize()
       
   770                     for page_idx in xrange(child.GetPageCount()):
       
   771                         page = child.GetWindowFromIdx(page_idx)
       
   772                         if not tab.has_key("size"):
       
   773                             tab["size"] = (tab_size[0], tab_size[1] + page.GetSize()[1])
       
   774                         tab_infos = self.GetTabInfos(page)
       
   775                         if tab_infos is not None:
       
   776                             tab["pages"].append((tab_infos, page_idx == child.GetActivePage()))
       
   777                     tabs.append(tab)
       
   778         tabs.sort(lambda x, y: cmp(x["pos"], y["pos"]))
       
   779         size = notebook.GetSize()
       
   780         return ComputeTabsLayout(tabs, wx.Rect(1, 1, size[0] - NOTEBOOK_BORDER, size[1] - NOTEBOOK_BORDER))
       
   781     
       
   782     def LoadTab(self, notebook, page_infos):
       
   783         if page_infos[0] == "main":
       
   784             infos = self.MainTabs.get(page_infos[1])
       
   785             if infos is not None:
       
   786                 page_ref, page_title = infos
       
   787                 notebook.AddPage(page_ref, page_title)
       
   788                 return notebook.GetPageIndex(page_ref)
       
   789         elif page_infos[0] == "editor":
       
   790             tagname = page_infos[1]
       
   791             page_ref = self.EditProjectElement(self.Controler.GetElementType(tagname), tagname)
       
   792             if page_ref is not None:
       
   793                 page_ref.RefreshView()
       
   794                 return notebook.GetPageIndex(page_ref)
       
   795         elif page_infos[0] == "debug":
       
   796             instance_path = page_infos[1]
       
   797             instance_infos = self.Controler.GetInstanceInfos(instance_path, self.EnableDebug)
       
   798             if instance_infos is not None:
       
   799                 return notebook.GetPageIndex(self.OpenDebugViewer(instance_infos["class"], instance_path, instance_infos["type"]))
       
   800         return None
       
   801             
       
   802     def LoadTabLayout(self, notebook, tabs, mode="all", first_index=None):
       
   803         if isinstance(tabs, ListType):
       
   804             if len(tabs) == 0:
       
   805                 return
       
   806             raise ValueError, "Not supported"
       
   807         
       
   808         if tabs.has_key("split"):
       
   809             self.LoadTabLayout(notebook, tabs["others"])
       
   810             
       
   811             split_dir, split_ratio = tabs["split"]
       
   812             first_index = self.LoadTabLayout(notebook, tabs["tab"], mode="first")
       
   813             notebook.Split(first_index, split_dir)
       
   814             self.LoadTabLayout(notebook, tabs["tab"], mode="others", first_index=first_index)
       
   815             
       
   816         elif mode == "first":
       
   817             return self.LoadTab(notebook, tabs["pages"][0][0])
       
   818         else:
       
   819             selected = first_index
       
   820             if mode == "others":
       
   821                 add_tabs = tabs["pages"][1:]
       
   822             else:
       
   823                 add_tabs = tabs["pages"]
       
   824             for page_infos, page_selected in add_tabs:
       
   825                 page_idx = self.LoadTab(notebook, page_infos)
       
   826                 if page_selected:
       
   827                     selected = page_idx
       
   828             if selected is not None:
       
   829                 wx.CallAfter(notebook.SetSelection, selected)
       
   830     
       
   831     def ResetPerspective(self):
       
   832         if self.DefaultPerspective is not None:
       
   833             self.AUIManager.LoadPerspective(self.DefaultPerspective["perspective"])
       
   834         
       
   835             for notebook in [self.LeftNoteBook, self.BottomNoteBook, self.RightNoteBook]:
       
   836                 for idx in xrange(notebook.GetPageCount()):
       
   837                     notebook.RemovePage(0)
       
   838                         
       
   839             notebooks = self.DefaultPerspective["notebooks"]
       
   840             for notebook, entry_name in [(self.LeftNoteBook, "leftnotebook"),
       
   841                                          (self.BottomNoteBook, "bottomnotebook"),
       
   842                                          (self.RightNoteBook, "rightnotebook")]:
       
   843                 self.LoadTabLayout(notebook, notebooks.get(entry_name))
       
   844     
       
   845             self._Refresh(EDITORTOOLBAR)
       
   846     
       
   847     def RestoreLastState(self):
       
   848         frame_size = None
       
   849         if self.Config.HasEntry("framesize"):
       
   850             frame_size = cPickle.loads(str(self.Config.Read("framesize")))
       
   851         
       
   852         self.Starting = True
       
   853         if frame_size is None:
       
   854             self.Maximize()
       
   855         else:
       
   856             self.SetClientSize(frame_size)
       
   857         
       
   858     def RestoreLastLayout(self):
       
   859         notebooks = {}
       
   860         for notebook, entry_name in [(self.LeftNoteBook, "leftnotebook"),
       
   861                                      (self.BottomNoteBook, "bottomnotebook"),
       
   862                                      (self.RightNoteBook, "rightnotebook")]:
       
   863             notebooks[entry_name] = self.SaveTabLayout(notebook)
       
   864         self.DefaultPerspective = {
       
   865             "perspective": self.AUIManager.SavePerspective(),
       
   866             "notebooks": notebooks,
       
   867         }
       
   868         
       
   869         try:
       
   870             if self.Config.HasEntry("perspective"):
       
   871                 self.AUIManager.LoadPerspective(unicode(self.Config.Read("perspective")))
       
   872         
       
   873             if self.Config.HasEntry("notebooks"):
       
   874                 notebooks = cPickle.loads(str(self.Config.Read("notebooks")))
       
   875                 
       
   876                 for notebook in [self.LeftNoteBook, self.BottomNoteBook, self.RightNoteBook]:
       
   877                     for idx in xrange(notebook.GetPageCount()):
       
   878                         notebook.RemovePage(0)
       
   879                         
       
   880                 for notebook, entry_name in [(self.LeftNoteBook, "leftnotebook"),
       
   881                                              (self.BottomNoteBook, "bottomnotebook"),
       
   882                                              (self.RightNoteBook, "rightnotebook")]:
       
   883                     self.LoadTabLayout(notebook, notebooks.get(entry_name))
       
   884         except:
       
   885             self.ResetPerspective()
       
   886         
       
   887         self.LoadProjectLayout()
       
   888         
       
   889         self._Refresh(EDITORTOOLBAR)
       
   890     
       
   891     def SaveLastState(self):
       
   892         if not self.IsMaximized():
       
   893             self.Config.Write("framesize", cPickle.dumps(self.GetClientSize()))
       
   894         elif self.Config.HasEntry("framesize"):
       
   895             self.Config.DeleteEntry("framesize")
       
   896         
       
   897         notebooks = {}
       
   898         for notebook, entry_name in [(self.LeftNoteBook, "leftnotebook"),
       
   899                                      (self.BottomNoteBook, "bottomnotebook"),
       
   900                                      (self.RightNoteBook, "rightnotebook")]:
       
   901             notebooks[entry_name] = self.SaveTabLayout(notebook)
       
   902         self.Config.Write("notebooks", cPickle.dumps(notebooks))
       
   903         
       
   904         pane = self.AUIManager.GetPane(self.TabsOpened)
       
   905         if pane.IsMaximized():
       
   906             self.AUIManager.RestorePane(pane)
       
   907         self.Config.Write("perspective", self.AUIManager.SavePerspective())
       
   908     
       
   909         self.SaveProjectLayout()
       
   910         
       
   911         for i in xrange(self.TabsOpened.GetPageCount()):
       
   912             self.SavePageState(self.TabsOpened.GetPage(i))
       
   913         
       
   914         self.Config.Flush()
       
   915 
       
   916     def SaveProjectLayout(self):
       
   917         if self.Controler is not None:
       
   918             tabs = []
       
   919             
       
   920             projects = {}
       
   921             try:
       
   922                  if self.Config.HasEntry("projects"):
       
   923                     projects = cPickle.loads(str(self.Config.Read("projects")))
       
   924             except:
       
   925                 pass
       
   926             
       
   927             project_infos = projects.setdefault(
       
   928                  EncodeFileSystemPath(os.path.realpath(self.Controler.GetFilePath())), {})
       
   929             project_infos["tabs"] = self.SaveTabLayout(self.TabsOpened)
       
   930             if self.EnableDebug:
       
   931                 project_infos["debug_vars"] = self.DebugVariablePanel.GetDebugVariables()
       
   932             
       
   933             self.Config.Write("projects", cPickle.dumps(projects))
       
   934             self.Config.Flush()
       
   935     
       
   936     def LoadProjectLayout(self):
       
   937         if self.Controler is not None:
       
   938             project = self.GetProjectConfiguration()
       
   939             
       
   940             try:
       
   941                 if project.has_key("tabs"):
       
   942                     self.LoadTabLayout(self.TabsOpened, project["tabs"])
       
   943             except:
       
   944                 self.DeleteAllPages()
       
   945                 
       
   946             if self.EnableDebug:
       
   947                 try:
       
   948                     for variable in project.get("debug_vars", []):
       
   949                         self.DebugVariablePanel.InsertValue(variable, force=True)
       
   950                 except:
       
   951                     self.DebugVariablePanel.ResetGrid()
       
   952             
       
   953 #-------------------------------------------------------------------------------
       
   954 #                               General Functions
       
   955 #-------------------------------------------------------------------------------
       
   956 
       
   957     def SetRefreshFunctions(self):
       
   958         self.RefreshFunctions = {
       
   959             TITLE : self.RefreshTitle,
       
   960             EDITORTOOLBAR : self.RefreshEditorToolBar,
       
   961             FILEMENU : self.RefreshFileMenu,
       
   962             EDITMENU : self.RefreshEditMenu,
       
   963             DISPLAYMENU : self.RefreshDisplayMenu,
       
   964             PROJECTTREE : self.RefreshProjectTree,
       
   965             POUINSTANCEVARIABLESPANEL : self.RefreshPouInstanceVariablesPanel, 
       
   966             LIBRARYTREE : self.RefreshLibraryPanel,
       
   967             SCALING : self.RefreshScaling,
       
   968             PAGETITLES: self.RefreshPageTitles}
       
   969 
       
   970     ## Call PLCOpenEditor refresh functions.
       
   971     #  @param elements List of elements to refresh.
       
   972     def _Refresh(self, *elements):
       
   973         try:
       
   974             for element in elements:
       
   975                 self.RefreshFunctions[element]()
       
   976         except wx.PyDeadObjectError:
       
   977             # ignore exceptions caused by refresh while quitting
       
   978             pass
       
   979 
       
   980     ## Callback function when AUINotebook Page closed with CloseButton
       
   981     #  @param event AUINotebook Event.
       
   982     def OnPageClose(self, event):
       
   983         selected = self.TabsOpened.GetSelection()
       
   984         if selected > -1:
       
   985             window = self.TabsOpened.GetPage(selected)
       
   986             
       
   987             if window.CheckSaveBeforeClosing():
       
   988                 self.SavePageState(window)
       
   989                 
       
   990                 # Refresh all window elements that have changed
       
   991                 wx.CallAfter(self._Refresh, TITLE, EDITORTOOLBAR, FILEMENU, EDITMENU, DISPLAYMENU)
       
   992                 wx.CallAfter(self.RefreshTabCtrlEvent)
       
   993                 wx.CallAfter(self.CloseFindInPouDialog)
       
   994                 event.Skip()
       
   995             else:
       
   996                 event.Veto()
       
   997         
       
   998 
       
   999     def GetCopyBuffer(self):
       
  1000         data = None
       
  1001         if wx.TheClipboard.Open():
       
  1002             dataobj = wx.TextDataObject()
       
  1003             if wx.TheClipboard.GetData(dataobj):
       
  1004                 data = dataobj.GetText()
       
  1005             wx.TheClipboard.Close()
       
  1006         return data
       
  1007         
       
  1008     def SetCopyBuffer(self, text):
       
  1009         if wx.TheClipboard.Open():
       
  1010             data = wx.TextDataObject()
       
  1011             data.SetText(text)
       
  1012             wx.TheClipboard.SetData(data)
       
  1013             wx.TheClipboard.Flush()
       
  1014             wx.TheClipboard.Close()
       
  1015         self.RefreshEditMenu()
       
  1016 
       
  1017     def GetDrawingMode(self):
       
  1018         return self.DrawingMode
       
  1019 
       
  1020     def RefreshScaling(self):
       
  1021         for i in xrange(self.TabsOpened.GetPageCount()):
       
  1022             editor = self.TabsOpened.GetPage(i)
       
  1023             editor.RefreshScaling()
       
  1024 
       
  1025     def EditProjectSettings(self):
       
  1026         old_values = self.Controler.GetProjectProperties()
       
  1027         dialog = ProjectDialog(self)
       
  1028         dialog.SetValues(old_values)
       
  1029         if dialog.ShowModal() == wx.ID_OK:
       
  1030             new_values = dialog.GetValues()
       
  1031             new_values["creationDateTime"] = old_values["creationDateTime"]
       
  1032             if new_values != old_values:
       
  1033                 self.Controler.SetProjectProperties(None, new_values)
       
  1034                 self._Refresh(TITLE, EDITORTOOLBAR, FILEMENU, EDITMENU, DISPLAYMENU, 
       
  1035                               PROJECTTREE, POUINSTANCEVARIABLESPANEL, SCALING)
       
  1036         dialog.Destroy()
       
  1037 
       
  1038 #-------------------------------------------------------------------------------
       
  1039 #                            Notebook Unified Functions
       
  1040 #-------------------------------------------------------------------------------
       
  1041     
       
  1042     ## Function that add a tab in Notebook, calling refresh for tab DClick event
       
  1043     # for wx.aui.AUINotebook.
       
  1044     #  @param window Panel to display in tab.
       
  1045     #  @param text title for the tab ctrl.
       
  1046     def AddPage(self, window, text):
       
  1047         self.TabsOpened.AddPage(window, text)
       
  1048         self.RefreshTabCtrlEvent()
       
  1049     
       
  1050     ## Function that add a tab in Notebook, calling refresh for tab DClick event
       
  1051     # for wx.aui.AUINotebook.
       
  1052     #  @param window Panel to display in tab.
       
  1053     #  @param text title for the tab ctrl.
       
  1054     def DeletePage(self, window):
       
  1055         for idx in xrange(self.TabsOpened.GetPageCount()):
       
  1056             if self.TabsOpened.GetPage(idx) == window:
       
  1057                 self.TabsOpened.DeletePage(idx)
       
  1058                 self.RefreshTabCtrlEvent()
       
  1059                 return 
       
  1060         
       
  1061     ## Function that fix difference in deleting all tabs between 
       
  1062     # wx.Notebook and wx.aui.AUINotebook.
       
  1063     def DeleteAllPages(self):
       
  1064         for idx in xrange(self.TabsOpened.GetPageCount()):
       
  1065             self.TabsOpened.DeletePage(0)
       
  1066         self.RefreshTabCtrlEvent()
       
  1067 
       
  1068     ## Function that fix difference in setting picture on tab between 
       
  1069     # wx.Notebook and wx.aui.AUINotebook.
       
  1070     #  @param idx Tab index.
       
  1071     #  @param bitmap wx.Bitmap to define on tab.
       
  1072     #  @return True if operation succeeded
       
  1073     def SetPageBitmap(self, idx, bitmap):
       
  1074         return self.TabsOpened.SetPageBitmap(idx, bitmap)
       
  1075 
       
  1076 #-------------------------------------------------------------------------------
       
  1077 #                         Dialog Message Functions
       
  1078 #-------------------------------------------------------------------------------
       
  1079 
       
  1080     ## Function displaying an Error dialog in PLCOpenEditor.
       
  1081     #  @param message The message to display.
       
  1082     def ShowErrorMessage(self, message):
       
  1083         dialog = wx.MessageDialog(self, message, _("Error"), wx.OK|wx.ICON_ERROR)
       
  1084         dialog.ShowModal()
       
  1085         dialog.Destroy()
       
  1086 
       
  1087     ## Function displaying an Error dialog in PLCOpenEditor.
       
  1088     #  @return False if closing cancelled.
       
  1089     def CheckSaveBeforeClosing(self, title=_("Close Project")):
       
  1090         if not self.Controler.ProjectIsSaved():
       
  1091             dialog = wx.MessageDialog(self, _("There are changes, do you want to save?"), title, wx.YES_NO|wx.CANCEL|wx.ICON_QUESTION)
       
  1092             answer = dialog.ShowModal()
       
  1093             dialog.Destroy()
       
  1094             if answer == wx.ID_YES:
       
  1095                 self.SaveProject()
       
  1096             elif answer == wx.ID_CANCEL:
       
  1097                 return False
       
  1098         
       
  1099         for idx in xrange(self.TabsOpened.GetPageCount()):
       
  1100             window = self.TabsOpened.GetPage(idx)
       
  1101             if not window.CheckSaveBeforeClosing():
       
  1102                 return False
       
  1103         
       
  1104         return True
       
  1105 
       
  1106 #-------------------------------------------------------------------------------
       
  1107 #                            File Menu Functions
       
  1108 #-------------------------------------------------------------------------------
       
  1109 
       
  1110     def RefreshFileMenu(self):
       
  1111         pass
       
  1112 
       
  1113     def ResetView(self):
       
  1114         self.DeleteAllPages()
       
  1115         self.ProjectTree.DeleteAllItems()
       
  1116         self.ProjectTree.Enable(False)
       
  1117         self.PouInstanceVariablesPanel.ResetView()
       
  1118         self.LibraryPanel.ResetTree()
       
  1119         self.LibraryPanel.SetController(None)
       
  1120         if self.EnableDebug:
       
  1121             self.DebugVariablePanel.ResetGrid()
       
  1122         self.Controler = None
       
  1123 
       
  1124     def OnCloseTabMenu(self, event):
       
  1125         selected = self.TabsOpened.GetSelection()
       
  1126         if selected >= 0:
       
  1127             self.TabsOpened.DeletePage(selected)
       
  1128             if self.TabsOpened.GetPageCount() > 0:
       
  1129                 new_index = min(selected, self.TabsOpened.GetPageCount() - 1)
       
  1130                 self.TabsOpened.SetSelection(new_index)
       
  1131         # Refresh all window elements that have changed
       
  1132         self._Refresh(TITLE, EDITORTOOLBAR, FILEMENU, EDITMENU, DISPLAYMENU)
       
  1133         self.RefreshTabCtrlEvent()
       
  1134 
       
  1135     def OnPageSetupMenu(self, event):
       
  1136         dialog = wx.PageSetupDialog(self, self.PageSetupData)
       
  1137         if dialog.ShowModal() == wx.ID_OK:
       
  1138             self.PageSetupData = wx.PageSetupDialogData(dialog.GetPageSetupData())
       
  1139             self.PrintData = wx.PrintData(self.PageSetupData.GetPrintData())
       
  1140         dialog.Destroy()
       
  1141 
       
  1142     def OnPreviewMenu(self, event):
       
  1143         selected = self.TabsOpened.GetSelection()        
       
  1144         if selected != -1:
       
  1145             window = self.TabsOpened.GetPage(selected)
       
  1146             data = wx.PrintDialogData(self.PrintData)
       
  1147             properties = self.Controler.GetProjectProperties(window.IsDebugging())
       
  1148             page_size = map(int, properties["pageSize"])
       
  1149             margins = (self.PageSetupData.GetMarginTopLeft(), self.PageSetupData.GetMarginBottomRight())
       
  1150             printout = GraphicPrintout(window, page_size, margins, True)
       
  1151             printout2 = GraphicPrintout(window, page_size, margins, True)
       
  1152             preview = wx.PrintPreview(printout, printout2, data)
       
  1153 
       
  1154             if preview.Ok():
       
  1155                 preview_frame = wx.PreviewFrame(preview, self, _("Print preview"), style=wx.DEFAULT_FRAME_STYLE|wx.FRAME_FLOAT_ON_PARENT)
       
  1156 
       
  1157                 preview_frame.Initialize()
       
  1158                 
       
  1159                 preview_canvas = preview.GetCanvas()
       
  1160                 preview_canvas.SetMinSize(preview_canvas.GetVirtualSize())
       
  1161                 preview_frame.Fit()
       
  1162                 
       
  1163                 preview_frame.Show(True)
       
  1164 
       
  1165     def OnPrintMenu(self, event):
       
  1166         selected = self.TabsOpened.GetSelection()        
       
  1167         if selected != -1:
       
  1168             window = self.TabsOpened.GetPage(selected)
       
  1169             dialog_data = wx.PrintDialogData(self.PrintData)
       
  1170             dialog_data.SetToPage(1)
       
  1171             properties = self.Controler.GetProjectProperties(window.IsDebugging())
       
  1172             page_size = map(int, properties["pageSize"])
       
  1173             margins = (self.PageSetupData.GetMarginTopLeft(), self.PageSetupData.GetMarginBottomRight())
       
  1174             printer = wx.Printer(dialog_data)
       
  1175             printout = GraphicPrintout(window, page_size, margins)
       
  1176             
       
  1177             if not printer.Print(self, printout, True) and printer.GetLastError() != wx.PRINTER_CANCELLED:
       
  1178                 self.ShowErrorMessage(_("There was a problem printing.\nPerhaps your current printer is not set correctly?"))
       
  1179             printout.Destroy()
       
  1180 
       
  1181     def OnPropertiesMenu(self, event):
       
  1182         self.EditProjectSettings()
       
  1183 
       
  1184     def OnQuitMenu(self, event):
       
  1185         self.Close()
       
  1186 
       
  1187 #-------------------------------------------------------------------------------
       
  1188 #                            Edit Menu Functions
       
  1189 #-------------------------------------------------------------------------------
       
  1190 
       
  1191     def RefreshEditMenu(self):
       
  1192         MenuToolBar = self.Panes["MenuToolBar"]
       
  1193         if self.Controler is not None:
       
  1194             selected = self.TabsOpened.GetSelection()
       
  1195             if selected > -1:
       
  1196                 window = self.TabsOpened.GetPage(selected)
       
  1197                 undo, redo = window.GetBufferState()
       
  1198             else:
       
  1199                 undo, redo = self.Controler.GetBufferState()
       
  1200             self.EditMenu.Enable(wx.ID_UNDO, undo)
       
  1201             MenuToolBar.EnableTool(wx.ID_UNDO, undo)
       
  1202             self.EditMenu.Enable(wx.ID_REDO, redo)
       
  1203             MenuToolBar.EnableTool(wx.ID_REDO, redo)
       
  1204             #self.EditMenu.Enable(ID_PLCOPENEDITOREDITMENUENABLEUNDOREDO, True)
       
  1205             #self.EditMenu.Check(ID_PLCOPENEDITOREDITMENUENABLEUNDOREDO, 
       
  1206             #                self.Controler.IsProjectBufferEnabled())
       
  1207             self.EditMenu.Enable(wx.ID_FIND, selected > -1)
       
  1208             self.EditMenu.Enable(ID_PLCOPENEDITOREDITMENUFINDNEXT, 
       
  1209                   selected > -1 and self.SearchParams is not None)
       
  1210             self.EditMenu.Enable(ID_PLCOPENEDITOREDITMENUFINDPREVIOUS, 
       
  1211                   selected > -1 and self.SearchParams is not None)
       
  1212             self.EditMenu.Enable(ID_PLCOPENEDITOREDITMENUSEARCHINPROJECT, True)
       
  1213             MenuToolBar.EnableTool(ID_PLCOPENEDITOREDITMENUSEARCHINPROJECT, True)
       
  1214             self.EditMenu.Enable(wx.ID_ADD, True)
       
  1215             self.EditMenu.Enable(wx.ID_DELETE, True)
       
  1216             if self.TabsOpened.GetPageCount() > 0:
       
  1217                 self.EditMenu.Enable(wx.ID_CUT, True)
       
  1218                 MenuToolBar.EnableTool(wx.ID_CUT, True)
       
  1219                 self.EditMenu.Enable(wx.ID_COPY, True)
       
  1220                 MenuToolBar.EnableTool(wx.ID_COPY, True)
       
  1221                 if self.GetCopyBuffer() is not None:
       
  1222                     self.EditMenu.Enable(wx.ID_PASTE, True)
       
  1223                     MenuToolBar.EnableTool(wx.ID_PASTE, True)
       
  1224                 else:
       
  1225                     self.EditMenu.Enable(wx.ID_PASTE, False)
       
  1226                     MenuToolBar.EnableTool(wx.ID_PASTE, False)
       
  1227                 self.EditMenu.Enable(wx.ID_SELECTALL, True)
       
  1228             else:
       
  1229                 self.EditMenu.Enable(wx.ID_CUT, False)
       
  1230                 MenuToolBar.EnableTool(wx.ID_CUT, False)
       
  1231                 self.EditMenu.Enable(wx.ID_COPY, False)
       
  1232                 MenuToolBar.EnableTool(wx.ID_COPY, False)
       
  1233                 self.EditMenu.Enable(wx.ID_PASTE, False)
       
  1234                 MenuToolBar.EnableTool(wx.ID_PASTE, False)
       
  1235                 self.EditMenu.Enable(wx.ID_SELECTALL, False)
       
  1236         else:
       
  1237             self.EditMenu.Enable(wx.ID_UNDO, False)
       
  1238             MenuToolBar.EnableTool(wx.ID_UNDO, False)
       
  1239             self.EditMenu.Enable(wx.ID_REDO, False)
       
  1240             MenuToolBar.EnableTool(wx.ID_REDO, False)
       
  1241             #self.EditMenu.Enable(ID_PLCOPENEDITOREDITMENUENABLEUNDOREDO, False)
       
  1242             self.EditMenu.Enable(wx.ID_CUT, False)
       
  1243             MenuToolBar.EnableTool(wx.ID_CUT, False)
       
  1244             self.EditMenu.Enable(wx.ID_COPY, False)
       
  1245             MenuToolBar.EnableTool(wx.ID_COPY, False)
       
  1246             self.EditMenu.Enable(wx.ID_PASTE, False)
       
  1247             MenuToolBar.EnableTool(wx.ID_PASTE, False)
       
  1248             self.EditMenu.Enable(wx.ID_SELECTALL, False)
       
  1249             self.EditMenu.Enable(wx.ID_FIND, False)
       
  1250             self.EditMenu.Enable(ID_PLCOPENEDITOREDITMENUFINDNEXT, False)
       
  1251             self.EditMenu.Enable(ID_PLCOPENEDITOREDITMENUFINDPREVIOUS, False)
       
  1252             self.EditMenu.Enable(ID_PLCOPENEDITOREDITMENUSEARCHINPROJECT, False)
       
  1253             MenuToolBar.EnableTool(ID_PLCOPENEDITOREDITMENUSEARCHINPROJECT, False)
       
  1254             self.EditMenu.Enable(wx.ID_ADD, False)
       
  1255             self.EditMenu.Enable(wx.ID_DELETE, False)
       
  1256     
       
  1257     def CloseTabsWithoutModel(self, refresh=True):
       
  1258         idxs = range(self.TabsOpened.GetPageCount())
       
  1259         idxs.reverse()
       
  1260         for idx in idxs:
       
  1261             window = self.TabsOpened.GetPage(idx)
       
  1262             if window.HasNoModel():
       
  1263                 self.TabsOpened.DeletePage(idx)
       
  1264         if refresh:
       
  1265             self.RefreshEditor()
       
  1266 
       
  1267     def OnUndoMenu(self, event):
       
  1268         selected = self.TabsOpened.GetSelection()
       
  1269         if selected != -1:
       
  1270             window = self.TabsOpened.GetPage(selected)
       
  1271             window.Undo()
       
  1272         else:
       
  1273             self.Controler.LoadPrevious()
       
  1274         self._Refresh(TITLE, FILEMENU, EDITMENU, PROJECTTREE, POUINSTANCEVARIABLESPANEL, LIBRARYTREE, 
       
  1275                       SCALING, PAGETITLES)    
       
  1276     
       
  1277     def OnRedoMenu(self, event):
       
  1278         selected = self.TabsOpened.GetSelection()
       
  1279         if selected != -1:
       
  1280             window = self.TabsOpened.GetPage(selected)
       
  1281             window.Redo()
       
  1282         else:
       
  1283             self.Controler.LoadNext()
       
  1284         self._Refresh(TITLE, FILEMENU, EDITMENU, PROJECTTREE, POUINSTANCEVARIABLESPANEL, LIBRARYTREE, 
       
  1285                       SCALING, PAGETITLES)
       
  1286     
       
  1287     def OnEnableUndoRedoMenu(self, event):
       
  1288         self.Controler.EnableProjectBuffer(event.IsChecked())
       
  1289         self.RefreshEditMenu()
       
  1290 
       
  1291     OnCutMenu = GetShortcutKeyCallbackFunction("Cut")
       
  1292     OnCopyMenu = GetShortcutKeyCallbackFunction("Copy")
       
  1293     OnPasteMenu = GetShortcutKeyCallbackFunction("Paste")
       
  1294 
       
  1295     def OnSelectAllMenu(self, event):
       
  1296         control = self.FindFocus()
       
  1297         if control is not None and control.GetName() == "Viewer":
       
  1298             control.Parent.SelectAll()
       
  1299         elif isinstance(control, wx.stc.StyledTextCtrl):
       
  1300             control.SelectAll()
       
  1301         elif isinstance(control, wx.TextCtrl):
       
  1302             control.SetSelection(0, control.GetLastPosition())
       
  1303         elif isinstance(control, wx.ComboBox):
       
  1304             control.SetMark(0, control.GetLastPosition() + 1)
       
  1305     
       
  1306     DeleteFunctions = {
       
  1307         ITEM_DATATYPE: GetDeleteElementFunction(PLCControler.ProjectRemoveDataType, check_function=PLCControler.DataTypeIsUsed),
       
  1308         ITEM_POU: GetDeleteElementFunction(PLCControler.ProjectRemovePou, check_function=PLCControler.PouIsUsed),
       
  1309         ITEM_TRANSITION: GetDeleteElementFunction(PLCControler.ProjectRemovePouTransition, ITEM_POU),
       
  1310         ITEM_ACTION: GetDeleteElementFunction(PLCControler.ProjectRemovePouAction, ITEM_POU),
       
  1311         ITEM_CONFIGURATION: GetDeleteElementFunction(PLCControler.ProjectRemoveConfiguration),
       
  1312         ITEM_RESOURCE: GetDeleteElementFunction(PLCControler.ProjectRemoveConfigurationResource, ITEM_CONFIGURATION)
       
  1313     }
       
  1314     
       
  1315     def OnDeleteMenu(self, event):
       
  1316         window = self.FindFocus()
       
  1317         if window == self.ProjectTree or window is None:
       
  1318             selected = self.ProjectTree.GetSelection()
       
  1319             if selected.IsOk():
       
  1320                 function = self.DeleteFunctions.get(self.ProjectTree.GetPyData(selected)["type"], None)
       
  1321                 if function is not None:
       
  1322                     function(self, selected)
       
  1323                     self.CloseTabsWithoutModel()
       
  1324                     self._Refresh(TITLE, EDITORTOOLBAR, FILEMENU, EDITMENU, PROJECTTREE, 
       
  1325                                   POUINSTANCEVARIABLESPANEL, LIBRARYTREE)
       
  1326         elif isinstance(window, (Viewer, TextViewer)):
       
  1327             event = wx.KeyEvent(wx.EVT_CHAR._getEvtType())
       
  1328             event.m_keyCode = wx.WXK_DELETE
       
  1329             window.ProcessEvent(event)
       
  1330 
       
  1331     def OnFindMenu(self, event):
       
  1332         if not self.FindDialog.IsShown():
       
  1333             self.FindDialog.Show()
       
  1334     
       
  1335     def CloseFindInPouDialog(self):
       
  1336         selected = self.TabsOpened.GetSelection()
       
  1337         if selected == -1 and self.FindDialog.IsShown():
       
  1338             self.FindDialog.Hide()
       
  1339     
       
  1340     def OnFindNextMenu(self, event):
       
  1341         self.FindInPou(1)
       
  1342     
       
  1343     def OnFindPreviousMenu(self, event):
       
  1344         self.FindInPou(-1)
       
  1345     
       
  1346     def FindInPou(self, direction, search_params=None):
       
  1347         if search_params is not None:
       
  1348             self.SearchParams = search_params
       
  1349         selected = self.TabsOpened.GetSelection()
       
  1350         if selected != -1:
       
  1351             window = self.TabsOpened.GetPage(selected)
       
  1352             window.Find(direction, self.SearchParams)
       
  1353     
       
  1354     def OnSearchInProjectMenu(self, event):
       
  1355         dialog = SearchInProjectDialog(self)
       
  1356         if dialog.ShowModal() == wx.ID_OK:
       
  1357             criteria = dialog.GetCriteria()
       
  1358             result = self.Controler.SearchInProject(criteria)
       
  1359             self.ClearSearchResults()
       
  1360             self.SearchResultPanel.SetSearchResults(criteria, result)
       
  1361             self.BottomNoteBook.SetSelection(self.BottomNoteBook.GetPageIndex(self.SearchResultPanel))
       
  1362             
       
  1363 #-------------------------------------------------------------------------------
       
  1364 #                             Display Menu Functions
       
  1365 #-------------------------------------------------------------------------------
       
  1366 
       
  1367     def RefreshDisplayMenu(self):
       
  1368         if self.Controler is not None:
       
  1369             if self.TabsOpened.GetPageCount() > 0:
       
  1370                 self.DisplayMenu.Enable(wx.ID_REFRESH, True)
       
  1371                 selected = self.TabsOpened.GetSelection()
       
  1372                 if selected != -1:
       
  1373                     window = self.TabsOpened.GetPage(selected)
       
  1374                     if isinstance(window, Viewer):
       
  1375                         self.DisplayMenu.Enable(wx.ID_ZOOM_FIT, True)
       
  1376                         zoommenu = self.DisplayMenu.FindItemById(wx.ID_ZOOM_FIT).GetSubMenu()
       
  1377                         zoomitem = zoommenu.FindItemByPosition(window.GetScale())
       
  1378                         zoomitem.Check(True)
       
  1379                     else:
       
  1380                         self.DisplayMenu.Enable(wx.ID_ZOOM_FIT, False)
       
  1381                 else:
       
  1382                     self.DisplayMenu.Enable(wx.ID_ZOOM_FIT, False)
       
  1383             else:
       
  1384                 self.DisplayMenu.Enable(wx.ID_REFRESH, False)
       
  1385                 self.DisplayMenu.Enable(wx.ID_ZOOM_FIT, False)
       
  1386             if self.EnableDebug:
       
  1387                 self.DisplayMenu.Enable(wx.ID_CLEAR, True)
       
  1388         else:
       
  1389             self.DisplayMenu.Enable(wx.ID_REFRESH, False)
       
  1390             if self.EnableDebug:
       
  1391                 self.DisplayMenu.Enable(wx.ID_CLEAR, False)
       
  1392             self.DisplayMenu.Enable(wx.ID_ZOOM_FIT, False)
       
  1393         
       
  1394     def OnRefreshMenu(self, event):
       
  1395         self.RefreshEditor()
       
  1396 
       
  1397     def OnClearErrorsMenu(self, event):
       
  1398         self.ClearErrors()
       
  1399 
       
  1400     def GenerateZoomFunction(self, idx):
       
  1401         def ZoomFunction(event):
       
  1402             selected = self.TabsOpened.GetSelection()
       
  1403             if selected != -1:
       
  1404                 window = self.TabsOpened.GetPage(selected)
       
  1405                 window.SetScale(idx)
       
  1406                 window.RefreshVisibleElements()
       
  1407                 window.RefreshScrollBars()
       
  1408             event.Skip()
       
  1409         return ZoomFunction
       
  1410 
       
  1411     def OnResetPerspective(self, event):
       
  1412         self.ResetPerspective()
       
  1413 
       
  1414 #-------------------------------------------------------------------------------
       
  1415 #                      Project Editor Panels Management Functions
       
  1416 #-------------------------------------------------------------------------------
       
  1417     
       
  1418     def OnPageDragged(self, event):
       
  1419         wx.CallAfter(self.RefreshTabCtrlEvent)
       
  1420         event.Skip()
       
  1421     
       
  1422     def OnAllowNotebookDnD(self, event):
       
  1423         event.Allow()
       
  1424     
       
  1425     def RefreshTabCtrlEvent(self):
       
  1426         auitabctrl = []
       
  1427         for child in self.TabsOpened.GetChildren():
       
  1428             if isinstance(child, wx.aui.AuiTabCtrl):
       
  1429                 auitabctrl.append(child)
       
  1430                 if child not in self.AuiTabCtrl:
       
  1431                     child.Bind(wx.EVT_LEFT_DCLICK, self.GetTabsOpenedDClickFunction(child))
       
  1432         self.AuiTabCtrl = auitabctrl
       
  1433         if self.TabsOpened.GetPageCount() == 0:
       
  1434             pane = self.AUIManager.GetPane(self.TabsOpened)
       
  1435             if pane.IsMaximized():
       
  1436                 self.AUIManager.RestorePane(pane)
       
  1437             self.AUIManager.Update()
       
  1438     
       
  1439     def EnsureTabVisible(self, tab):
       
  1440         notebook = tab.GetParent()
       
  1441         notebook.SetSelection(notebook.GetPageIndex(tab))
       
  1442     
       
  1443     def OnPouSelectedChanging(self, event):
       
  1444         if not self.Starting:
       
  1445             selected = self.TabsOpened.GetSelection()
       
  1446             if selected >= 0:
       
  1447                 window = self.TabsOpened.GetPage(selected)
       
  1448                 if not window.IsDebugging():
       
  1449                     window.ResetBuffer()
       
  1450         event.Skip()
       
  1451     
       
  1452     def OnPouSelectedChanged(self, event):
       
  1453         if not self.Starting:
       
  1454             selected = self.TabsOpened.GetSelection()
       
  1455             if selected >= 0:
       
  1456                 window = self.TabsOpened.GetPage(selected)
       
  1457                 tagname = window.GetTagName()
       
  1458                 if not window.IsDebugging():
       
  1459                     wx.CallAfter(self.SelectProjectTreeItem, tagname)
       
  1460                     wx.CallAfter(self.PouInstanceVariablesPanel.SetPouType, tagname)
       
  1461                     window.RefreshView()
       
  1462                     self.EnsureTabVisible(self.LibraryPanel)
       
  1463                 else:
       
  1464                     instance_path = window.GetInstancePath()
       
  1465                     if tagname == "":
       
  1466                         instance_path = instance_path.rsplit(".", 1)[0]
       
  1467                         tagname = self.Controler.GetPouInstanceTagName(instance_path, self.EnableDebug)
       
  1468                     self.EnsureTabVisible(self.DebugVariablePanel)
       
  1469                     wx.CallAfter(self.PouInstanceVariablesPanel.SetPouType, tagname, instance_path)
       
  1470             wx.CallAfter(self._Refresh, FILEMENU, EDITMENU, DISPLAYMENU, EDITORTOOLBAR)
       
  1471         event.Skip()
       
  1472         
       
  1473     def RefreshEditor(self):
       
  1474         selected = self.TabsOpened.GetSelection()
       
  1475         if selected >= 0:
       
  1476             window = self.TabsOpened.GetPage(selected)
       
  1477             tagname = window.GetTagName()
       
  1478             if not window.IsDebugging():
       
  1479                 self.SelectProjectTreeItem(tagname)
       
  1480                 self.PouInstanceVariablesPanel.SetPouType(tagname)
       
  1481             else:
       
  1482                 instance_path = window.GetInstancePath()
       
  1483                 if tagname == "":
       
  1484                     instance_path = instance_path.rsplit(".", 1)[0]
       
  1485                     tagname = self.Controler.GetPouInstanceTagName(instance_path, self.EnableDebug)
       
  1486                 self.PouInstanceVariablesPanel.SetPouType(tagname, instance_path)
       
  1487             for child in self.TabsOpened.GetChildren():
       
  1488                 if isinstance(child, wx.aui.AuiTabCtrl):
       
  1489                     active_page = child.GetActivePage()
       
  1490                     if active_page >= 0:
       
  1491                         window = child.GetWindowFromIdx(active_page)
       
  1492                         window.RefreshView()
       
  1493             self._Refresh(FILEMENU, EDITMENU, DISPLAYMENU, EDITORTOOLBAR)
       
  1494     
       
  1495     def RefreshEditorNames(self, old_tagname, new_tagname):
       
  1496         for i in xrange(self.TabsOpened.GetPageCount()):
       
  1497             editor = self.TabsOpened.GetPage(i)
       
  1498             if editor.GetTagName() == old_tagname:
       
  1499                 editor.SetTagName(new_tagname)
       
  1500     
       
  1501     def IsOpened(self, tagname):
       
  1502         for idx in xrange(self.TabsOpened.GetPageCount()):
       
  1503             if self.TabsOpened.GetPage(idx).IsViewing(tagname):
       
  1504                 return idx
       
  1505         return None
       
  1506 
       
  1507     def RefreshPageTitles(self):
       
  1508         for idx in xrange(self.TabsOpened.GetPageCount()):
       
  1509             window = self.TabsOpened.GetPage(idx)
       
  1510             icon = window.GetIcon()
       
  1511             if icon is not None:
       
  1512                 self.SetPageBitmap(idx, icon)
       
  1513             self.TabsOpened.SetPageText(idx, window.GetTitle())
       
  1514 
       
  1515     def GetTabsOpenedDClickFunction(self, tabctrl):
       
  1516         def OnTabsOpenedDClick(event):
       
  1517             pos = event.GetPosition()
       
  1518             if tabctrl.TabHitTest(pos.x, pos.y, None):
       
  1519                 pane = self.AUIManager.GetPane(self.TabsOpened)
       
  1520                 if pane.IsMaximized():
       
  1521                     self.AUIManager.RestorePane(pane)
       
  1522                 else:
       
  1523                     self.AUIManager.MaximizePane(pane)
       
  1524                 self.AUIManager.Update()
       
  1525             event.Skip()
       
  1526         return OnTabsOpenedDClick
       
  1527 
       
  1528 #-------------------------------------------------------------------------------
       
  1529 #                         Types Tree Management Functions
       
  1530 #-------------------------------------------------------------------------------
       
  1531 
       
  1532     def RefreshProjectTree(self):
       
  1533         infos = self.Controler.GetProjectInfos()
       
  1534         root = self.ProjectTree.GetRootItem()
       
  1535         if not root.IsOk():
       
  1536             root = self.ProjectTree.AddRoot(infos["name"])
       
  1537         self.GenerateProjectTreeBranch(root, infos)
       
  1538         self.ProjectTree.Expand(root)
       
  1539 
       
  1540     def ResetSelectedItem(self):
       
  1541         self.SelectedItem = None
       
  1542 
       
  1543     def GenerateProjectTreeBranch(self, root, infos):
       
  1544         to_delete = []
       
  1545         item_name = infos["name"]
       
  1546         if infos["type"] in ITEMS_UNEDITABLE:
       
  1547             if len(infos["values"]) == 1:
       
  1548                 return self.GenerateProjectTreeBranch(root, infos["values"][0])
       
  1549             item_name = _(item_name)
       
  1550         self.ProjectTree.SetItemText(root, item_name)
       
  1551         self.ProjectTree.SetPyData(root, infos)
       
  1552         highlight_colours = self.Highlights.get(infos.get("tagname", None), (wx.WHITE, wx.BLACK))
       
  1553         self.ProjectTree.SetItemBackgroundColour(root, highlight_colours[0])
       
  1554         self.ProjectTree.SetItemTextColour(root, highlight_colours[1])
       
  1555         if infos["type"] == ITEM_POU:
       
  1556             self.ProjectTree.SetItemImage(root, self.TreeImageDict[self.Controler.GetPouBodyType(infos["name"])])
       
  1557         elif infos.has_key("icon") and infos["icon"] is not None:
       
  1558             icon_name = infos["icon"]
       
  1559             if not self.TreeImageDict.has_key(icon_name):
       
  1560                 self.TreeImageDict[icon_name] = self.TreeImageList.Add(GetBitmap(icon_name))
       
  1561             self.ProjectTree.SetItemImage(root, self.TreeImageDict[icon_name])
       
  1562         elif self.TreeImageDict.has_key(infos["type"]):
       
  1563             self.ProjectTree.SetItemImage(root, self.TreeImageDict[infos["type"]])      
       
  1564         
       
  1565         if wx.VERSION >= (2, 6, 0):
       
  1566             item, root_cookie = self.ProjectTree.GetFirstChild(root)
       
  1567         else:
       
  1568             item, root_cookie = self.ProjectTree.GetFirstChild(root, 0)
       
  1569         for values in infos["values"]:
       
  1570             if values["type"] not in ITEMS_UNEDITABLE or len(values["values"]) > 0:
       
  1571                 if not item.IsOk():
       
  1572                     item = self.ProjectTree.AppendItem(root, "")
       
  1573                     if wx.Platform != '__WXMSW__':
       
  1574                         item, root_cookie = self.ProjectTree.GetNextChild(root, root_cookie)
       
  1575                 self.GenerateProjectTreeBranch(item, values)
       
  1576                 item, root_cookie = self.ProjectTree.GetNextChild(root, root_cookie)
       
  1577         while item.IsOk():
       
  1578             to_delete.append(item)
       
  1579             item, root_cookie = self.ProjectTree.GetNextChild(root, root_cookie)
       
  1580         for item in to_delete:
       
  1581             self.ProjectTree.Delete(item)
       
  1582 
       
  1583     def SelectProjectTreeItem(self, tagname):
       
  1584         if self.ProjectTree is not None:
       
  1585             root = self.ProjectTree.GetRootItem()
       
  1586             if root.IsOk():
       
  1587                 words = tagname.split("::")
       
  1588                 if words[0] == "D":
       
  1589                     return self.RecursiveProjectTreeItemSelection(root, [(words[1], ITEM_DATATYPE)])
       
  1590                 elif words[0] == "P":
       
  1591                     return self.RecursiveProjectTreeItemSelection(root, [(words[1], ITEM_POU)])
       
  1592                 elif words[0] == "T":
       
  1593                     return self.RecursiveProjectTreeItemSelection(root, [(words[1], ITEM_POU), (words[2], ITEM_TRANSITION)])
       
  1594                 elif words[0] == "A":
       
  1595                     return self.RecursiveProjectTreeItemSelection(root, [(words[1], ITEM_POU), (words[2], ITEM_ACTION)])
       
  1596                 elif words[0] == "C":
       
  1597                     return self.RecursiveProjectTreeItemSelection(root, [(words[1], ITEM_CONFIGURATION)])
       
  1598                 elif words[0] == "R":
       
  1599                     return self.RecursiveProjectTreeItemSelection(root, [(words[1], ITEM_CONFIGURATION), (words[2], ITEM_RESOURCE)])
       
  1600         return False
       
  1601 
       
  1602     def RecursiveProjectTreeItemSelection(self, root, items):
       
  1603         found = False
       
  1604         if wx.VERSION >= (2, 6, 0):
       
  1605             item, root_cookie = self.ProjectTree.GetFirstChild(root)
       
  1606         else:
       
  1607             item, root_cookie = self.ProjectTree.GetFirstChild(root, 0)
       
  1608         while item.IsOk() and not found:
       
  1609             item_infos = self.ProjectTree.GetPyData(item)
       
  1610             if (item_infos["name"].split(":")[-1].strip(), item_infos["type"]) == items[0]:
       
  1611                 if len(items) == 1:
       
  1612                     self.SelectedItem = item
       
  1613                     wx.CallAfter(self.ProjectTree.SelectItem, item)
       
  1614                     wx.CallAfter(self.ResetSelectedItem)
       
  1615                     return True
       
  1616                 else:
       
  1617                     found = self.RecursiveProjectTreeItemSelection(item, items[1:])
       
  1618             else:
       
  1619                 found = self.RecursiveProjectTreeItemSelection(item, items)
       
  1620             item, root_cookie = self.ProjectTree.GetNextChild(root, root_cookie)
       
  1621         return found
       
  1622 
       
  1623     def OnProjectTreeBeginDrag(self, event):
       
  1624         if wx.Platform == '__WXMSW__':
       
  1625             self.SelectedItem = event.GetItem()
       
  1626         if self.SelectedItem is not None and self.ProjectTree.GetPyData(self.SelectedItem)["type"] == ITEM_POU:
       
  1627             block_name = self.ProjectTree.GetItemText(self.SelectedItem)
       
  1628             block_type = self.Controler.GetPouType(block_name)
       
  1629             if block_type != "program":
       
  1630                 data = wx.TextDataObject(str((block_name, block_type, "")))
       
  1631                 dragSource = wx.DropSource(self.ProjectTree)
       
  1632                 dragSource.SetData(data)
       
  1633                 dragSource.DoDragDrop()
       
  1634             self.ResetSelectedItem()
       
  1635 
       
  1636     def OnProjectTreeItemBeginEdit(self, event):
       
  1637         selected = event.GetItem()
       
  1638         if self.ProjectTree.GetPyData(selected)["type"] in ITEMS_UNEDITABLE:
       
  1639             event.Veto()
       
  1640         else:
       
  1641             event.Skip()
       
  1642 
       
  1643     def OnProjectTreeItemEndEdit(self, event):
       
  1644         message = None
       
  1645         abort = False
       
  1646         new_name = event.GetLabel()
       
  1647         if new_name != "":
       
  1648             if not TestIdentifier(new_name):
       
  1649                 message = _("\"%s\" is not a valid identifier!")%new_name
       
  1650             elif new_name.upper() in IEC_KEYWORDS:
       
  1651                 message = _("\"%s\" is a keyword. It can't be used!")%new_name
       
  1652             else:
       
  1653                 item = event.GetItem()
       
  1654                 old_name = self.ProjectTree.GetItemText(item)
       
  1655                 item_infos = self.ProjectTree.GetPyData(item)
       
  1656                 if item_infos["type"] == ITEM_PROJECT:
       
  1657                     self.Controler.SetProjectProperties(name = new_name)
       
  1658                 elif item_infos["type"] == ITEM_DATATYPE:
       
  1659                     if new_name.upper() in [name.upper() for name in self.Controler.GetProjectDataTypeNames() if name != old_name]:
       
  1660                         message = _("\"%s\" data type already exists!")%new_name
       
  1661                         abort = True
       
  1662                     if not abort:
       
  1663                         self.Controler.ChangeDataTypeName(old_name, new_name)
       
  1664                         self.RefreshEditorNames(self.Controler.ComputeDataTypeName(old_name), 
       
  1665                                                 self.Controler.ComputeDataTypeName(new_name))
       
  1666                         self.RefreshPageTitles()
       
  1667                 elif item_infos["type"] == ITEM_POU:
       
  1668                     if new_name.upper() in [name.upper() for name in self.Controler.GetProjectPouNames() if name != old_name]:
       
  1669                         message = _("\"%s\" pou already exists!")%new_name
       
  1670                         abort = True
       
  1671                     elif new_name.upper() in [name.upper() for name in self.Controler.GetProjectPouVariables()]:
       
  1672                         messageDialog = wx.MessageDialog(self, _("A POU has an element named \"%s\". This could cause a conflict. Do you wish to continue?")%new_name, _("Error"), wx.YES_NO|wx.ICON_QUESTION)
       
  1673                         if messageDialog.ShowModal() == wx.ID_NO:
       
  1674                             abort = True
       
  1675                         messageDialog.Destroy()
       
  1676                     if not abort:
       
  1677                         self.Controler.ChangePouName(old_name, new_name)
       
  1678                         self.RefreshEditorNames(self.Controler.ComputePouName(old_name), 
       
  1679                                                 self.Controler.ComputePouName(new_name))
       
  1680                         self.RefreshLibraryPanel()
       
  1681                         self.RefreshPageTitles()
       
  1682                 elif item_infos["type"] == ITEM_TRANSITION:
       
  1683                     if new_name.upper() in [name.upper() for name in self.Controler.GetProjectPouNames()]:
       
  1684                         message = _("A POU named \"%s\" already exists!")%new_name
       
  1685                     elif new_name.upper() in [name.upper() for name in self.Controler.GetProjectPouVariables(pou_name) if name != old_name]:
       
  1686                         message = _("A variable with \"%s\" as name already exists in this pou!")%new_name
       
  1687                     else:
       
  1688                         words = item_infos["tagname"].split("::")
       
  1689                         self.Controler.ChangePouTransitionName(words[1], old_name, new_name)
       
  1690                         self.RefreshEditorNames(self.Controler.ComputePouTransitionName(words[1], old_name), 
       
  1691                                                 self.Controler.ComputePouTransitionName(words[1], new_name))
       
  1692                         self.RefreshPageTitles()
       
  1693                 elif item_infos["type"] == ITEM_ACTION:
       
  1694                     if new_name.upper() in [name.upper() for name in self.Controler.GetProjectPouNames()]:
       
  1695                         message = _("A POU named \"%s\" already exists!")%new_name
       
  1696                     elif new_name.upper() in [name.upper() for name in self.Controler.GetProjectPouVariables(pou_name) if name != old_name]:
       
  1697                         message = _("A variable with \"%s\" as name already exists in this pou!")%new_name
       
  1698                     else:
       
  1699                         words = item_infos["tagname"].split("::")
       
  1700                         self.Controler.ChangePouActionName(words[1], old_name, new_name)
       
  1701                         self.RefreshEditorNames(self.Controler.ComputePouActionName(words[1], old_name), 
       
  1702                                                 self.Controler.ComputePouActionName(words[1], new_name))
       
  1703                         self.RefreshPageTitles()
       
  1704                 elif item_infos["type"] == ITEM_CONFIGURATION:
       
  1705                     if new_name.upper() in [name.upper() for name in self.Controler.GetProjectConfigNames() if name != old_name]:
       
  1706                         message = _("\"%s\" config already exists!")%new_name
       
  1707                         abort = True
       
  1708                     elif new_name.upper() in [name.upper() for name in self.Controler.GetProjectPouNames()]:
       
  1709                         messageDialog = wx.MessageDialog(self, _("There is a POU named \"%s\". This could cause a conflict. Do you wish to continue?")%new_name, _("Error"), wx.YES_NO|wx.ICON_QUESTION)
       
  1710                         if messageDialog.ShowModal() == wx.ID_NO:
       
  1711                             abort = True
       
  1712                         messageDialog.Destroy()
       
  1713                     elif new_name.upper() in [name.upper() for name in self.Controler.GetProjectPouVariables()]:
       
  1714                         messageDialog = wx.MessageDialog(self, _("A POU has an element named \"%s\". This could cause a conflict. Do you wish to continue?")%new_name, _("Error"), wx.YES_NO|wx.ICON_QUESTION)
       
  1715                         if messageDialog.ShowModal() == wx.ID_NO:
       
  1716                             abort = True
       
  1717                         messageDialog.Destroy()
       
  1718                     if not abort:
       
  1719                         self.Controler.ChangeConfigurationName(old_name, new_name)
       
  1720                         self.RefreshEditorNames(self.Controler.ComputeConfigurationName(old_name), 
       
  1721                                                 self.Controler.ComputeConfigurationName(new_name))
       
  1722                         self.RefreshPageTitles()
       
  1723                 elif item_infos["type"] == ITEM_RESOURCE:
       
  1724                     if new_name.upper() in [name.upper() for name in self.Controler.GetProjectConfigNames()]:
       
  1725                         message = _("\"%s\" config already exists!")%new_name
       
  1726                         abort = True
       
  1727                     elif new_name.upper() in [name.upper() for name in self.Controler.GetProjectPouNames()]:
       
  1728                         messageDialog = wx.MessageDialog(self, _("There is a POU named \"%s\". This could cause a conflict. Do you wish to continue?")%new_name, _("Error"), wx.YES_NO|wx.ICON_QUESTION)
       
  1729                         if messageDialog.ShowModal() == wx.ID_NO:
       
  1730                             abort = True
       
  1731                         messageDialog.Destroy()
       
  1732                     elif new_name.upper() in [name.upper() for name in self.Controler.GetProjectPouVariables()]:
       
  1733                         messageDialog = wx.MessageDialog(self, _("A POU has an element named \"%s\". This could cause a conflict. Do you wish to continue?")%new_name, _("Error"), wx.YES_NO|wx.ICON_QUESTION)
       
  1734                         if messageDialog.ShowModal() == wx.ID_NO:
       
  1735                             abort = True
       
  1736                         messageDialog.Destroy()
       
  1737                     if not abort:
       
  1738                         words = item_infos["tagname"].split("::")
       
  1739                         self.Controler.ChangeConfigurationResourceName(words[1], old_name, new_name)
       
  1740                         self.RefreshEditorNames(self.Controler.ComputeConfigurationResourceName(words[1], old_name), 
       
  1741                                                 self.Controler.ComputeConfigurationResourceName(words[1], new_name))
       
  1742                         self.RefreshPageTitles()
       
  1743             if message or abort:
       
  1744                 if message:
       
  1745                     self.ShowErrorMessage(message)
       
  1746                 item = event.GetItem()
       
  1747                 wx.CallAfter(self.ProjectTree.EditLabel, item)
       
  1748                 event.Veto()
       
  1749             else:
       
  1750                 wx.CallAfter(self.RefreshProjectTree)
       
  1751                 self.RefreshEditor()
       
  1752                 self._Refresh(TITLE, FILEMENU, EDITMENU)
       
  1753                 event.Skip()
       
  1754     
       
  1755     def OnProjectTreeItemActivated(self, event):
       
  1756         selected = event.GetItem()
       
  1757         name = self.ProjectTree.GetItemText(selected)
       
  1758         item_infos = self.ProjectTree.GetPyData(selected)
       
  1759         if item_infos["type"] == ITEM_PROJECT:
       
  1760             self.EditProjectSettings()
       
  1761         else:
       
  1762             if item_infos["type"] in [ITEM_DATATYPE, ITEM_POU,
       
  1763                                     ITEM_CONFIGURATION, ITEM_RESOURCE,
       
  1764                                     ITEM_TRANSITION, ITEM_ACTION]:
       
  1765                 self.EditProjectElement(item_infos["type"], item_infos["tagname"])
       
  1766             event.Skip()
       
  1767     
       
  1768     def ProjectTreeItemSelect(self, select_item):
       
  1769         name = self.ProjectTree.GetItemText(select_item)
       
  1770         item_infos = self.ProjectTree.GetPyData(select_item)
       
  1771         if item_infos["type"] in [ITEM_DATATYPE, ITEM_POU,
       
  1772                                   ITEM_CONFIGURATION, ITEM_RESOURCE,
       
  1773                                   ITEM_TRANSITION, ITEM_ACTION]:
       
  1774             self.EditProjectElement(item_infos["type"], item_infos["tagname"], True)
       
  1775             self.PouInstanceVariablesPanel.SetPouType(item_infos["tagname"])
       
  1776         
       
  1777     def OnProjectTreeLeftUp(self, event):
       
  1778         if self.SelectedItem is not None:
       
  1779             self.ProjectTree.SelectItem(self.SelectedItem)
       
  1780             self.ProjectTreeItemSelect(self.SelectedItem)
       
  1781             wx.CallAfter(self.ResetSelectedItem)
       
  1782         event.Skip()
       
  1783     
       
  1784     def OnProjectTreeItemSelected(self, event):
       
  1785         self.ProjectTreeItemSelect(event.GetItem())
       
  1786         event.Skip()
       
  1787     
       
  1788     def OnProjectTreeItemChanging(self, event):
       
  1789         if self.ProjectTree.GetPyData(event.GetItem())["type"] not in ITEMS_UNEDITABLE and self.SelectedItem is None:
       
  1790             self.SelectedItem = event.GetItem()
       
  1791             event.Veto()
       
  1792         else:
       
  1793             event.Skip()
       
  1794     
       
  1795     def EditProjectElement(self, element, tagname, onlyopened = False):
       
  1796         openedidx = self.IsOpened(tagname)
       
  1797         if openedidx is not None:
       
  1798             old_selected = self.TabsOpened.GetSelection()
       
  1799             if old_selected != openedidx:
       
  1800                 if old_selected >= 0:
       
  1801                     self.TabsOpened.GetPage(old_selected).ResetBuffer()
       
  1802                 self.TabsOpened.SetSelection(openedidx)
       
  1803             self._Refresh(FILEMENU, EDITMENU, EDITORTOOLBAR, PAGETITLES)
       
  1804         elif not onlyopened:
       
  1805             new_window = None
       
  1806             if element == ITEM_CONFIGURATION:
       
  1807                 new_window = ConfigurationEditor(self.TabsOpened, tagname, self, self.Controler)
       
  1808                 new_window.SetIcon(GetBitmap("CONFIGURATION"))
       
  1809                 self.AddPage(new_window, "")
       
  1810             elif element == ITEM_RESOURCE:
       
  1811                 new_window = ResourceEditor(self.TabsOpened, tagname, self, self.Controler)
       
  1812                 new_window.SetIcon(GetBitmap("RESOURCE"))
       
  1813                 self.AddPage(new_window, "")
       
  1814             elif element in [ITEM_POU, ITEM_TRANSITION, ITEM_ACTION]:
       
  1815                 bodytype = self.Controler.GetEditedElementBodyType(tagname)
       
  1816                 if bodytype == "FBD":
       
  1817                     new_window = Viewer(self.TabsOpened, tagname, self, self.Controler)
       
  1818                     new_window.RefreshScaling(False)
       
  1819                 elif bodytype == "LD":
       
  1820                     new_window = LD_Viewer(self.TabsOpened, tagname, self, self.Controler)
       
  1821                     new_window.RefreshScaling(False)
       
  1822                 elif bodytype == "SFC":
       
  1823                     new_window = SFC_Viewer(self.TabsOpened, tagname, self, self.Controler)
       
  1824                     new_window.RefreshScaling(False)
       
  1825                 else:
       
  1826                     new_window = TextViewer(self.TabsOpened, tagname, self, self.Controler)
       
  1827                     new_window.SetTextSyntax(bodytype)
       
  1828                     if bodytype == "IL":
       
  1829                         new_window.SetKeywords(IL_KEYWORDS)
       
  1830                     else:
       
  1831                         new_window.SetKeywords(ST_KEYWORDS)
       
  1832                 if element == ITEM_POU:
       
  1833                     pou_type = self.Controler.GetEditedElementType(tagname)[1].upper()
       
  1834                     icon = GetBitmap(pou_type, bodytype)
       
  1835                 elif element == ITEM_TRANSITION:
       
  1836                     icon = GetBitmap("TRANSITION", bodytype)
       
  1837                 elif element == ITEM_ACTION:
       
  1838                     icon = GetBitmap("ACTION", bodytype)
       
  1839                 new_window.SetIcon(icon)
       
  1840                 self.AddPage(new_window, "")
       
  1841             elif element == ITEM_DATATYPE:
       
  1842                 new_window = DataTypeEditor(self.TabsOpened, tagname, self, self.Controler)
       
  1843                 new_window.SetIcon(GetBitmap("DATATYPE"))
       
  1844                 self.AddPage(new_window, "")
       
  1845             elif isinstance(element, EditorPanel):
       
  1846                 new_window = element
       
  1847                 self.AddPage(element, "")
       
  1848             if new_window is not None:
       
  1849                 project_infos = self.GetProjectConfiguration()
       
  1850                 if project_infos.has_key("editors_state"):
       
  1851                     state = project_infos["editors_state"].get(tagname)
       
  1852                     if state is not None:
       
  1853                         wx.CallAfter(new_window.SetState, state)
       
  1854                 
       
  1855                 openedidx = self.IsOpened(tagname)
       
  1856                 old_selected = self.TabsOpened.GetSelection()
       
  1857                 if old_selected != openedidx:
       
  1858                     if old_selected >= 0:
       
  1859                         self.TabsOpened.GetPage(old_selected).ResetBuffer()
       
  1860                 for i in xrange(self.TabsOpened.GetPageCount()):
       
  1861                     window = self.TabsOpened.GetPage(i)
       
  1862                     if window == new_window:
       
  1863                         self.TabsOpened.SetSelection(i)
       
  1864                         window.SetFocus()
       
  1865                 self.RefreshPageTitles()
       
  1866             return new_window
       
  1867     
       
  1868     def OnProjectTreeRightUp(self, event):
       
  1869         if wx.Platform == '__WXMSW__':
       
  1870             item = event.GetItem()
       
  1871         else:
       
  1872             item, flags = self.ProjectTree.HitTest(wx.Point(event.GetX(), event.GetY()))
       
  1873         self.ProjectTree.SelectItem(item)
       
  1874         self.ProjectTreeItemSelect(item)
       
  1875         name = self.ProjectTree.GetItemText(item)
       
  1876         item_infos = self.ProjectTree.GetPyData(item)
       
  1877         
       
  1878         menu = None
       
  1879         if item_infos["type"] in ITEMS_UNEDITABLE + [ITEM_PROJECT]:
       
  1880             if item_infos["type"] == ITEM_PROJECT:
       
  1881                 name = "Project"
       
  1882             else:
       
  1883                 name = UNEDITABLE_NAMES_DICT[name]
       
  1884             
       
  1885             if name == "Data Types":
       
  1886                 menu = wx.Menu(title='')
       
  1887                 new_id = wx.NewId()
       
  1888                 AppendMenu(menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Add DataType"))
       
  1889                 self.Bind(wx.EVT_MENU, self.OnAddDataTypeMenu, id=new_id)
       
  1890             
       
  1891             elif name in ["Functions", "Function Blocks", "Programs", "Project"]:
       
  1892                 menu = wx.Menu(title='')
       
  1893                 
       
  1894                 if name != "Project":
       
  1895                     new_id = wx.NewId()
       
  1896                     AppendMenu(menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Add POU"))
       
  1897                     self.Bind(wx.EVT_MENU, self.GenerateAddPouFunction({"Functions" : "function", "Function Blocks" : "functionBlock", "Programs" : "program"}[name]), id=new_id)
       
  1898 
       
  1899                 new_id = wx.NewId()
       
  1900                 AppendMenu(menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Paste POU"))
       
  1901                 self.Bind(wx.EVT_MENU, self.OnPastePou, id=new_id)
       
  1902                 if self.GetCopyBuffer() is None:
       
  1903                     menu.Enable(new_id, False)
       
  1904 
       
  1905             elif name == "Configurations":
       
  1906                 menu = wx.Menu(title='')
       
  1907                 new_id = wx.NewId()
       
  1908                 AppendMenu(menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Add Configuration"))
       
  1909                 self.Bind(wx.EVT_MENU, self.OnAddConfigurationMenu, id=new_id)
       
  1910             
       
  1911             elif name == "Transitions":
       
  1912                 menu = wx.Menu(title='')
       
  1913                 new_id = wx.NewId()
       
  1914                 AppendMenu(menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Add Transition"))
       
  1915                 parent = self.ProjectTree.GetItemParent(item)["type"]
       
  1916                 parent_type = self.ProjectTree.GetPyData(parent)
       
  1917                 while parent_type != ITEM_POU:
       
  1918                     parent = self.ProjectTree.GetItemParent(parent)
       
  1919                     parent_type = self.ProjectTree.GetPyData(parent)["type"]
       
  1920                 self.Bind(wx.EVT_MENU, self.GenerateAddTransitionFunction(self.ProjectTree.GetItemText(parent)), id=new_id)
       
  1921             
       
  1922             elif name == "Actions":
       
  1923                 menu = wx.Menu(title='')
       
  1924                 new_id = wx.NewId()
       
  1925                 AppendMenu(menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Add Action"))
       
  1926                 parent = self.ProjectTree.GetItemParent(item)
       
  1927                 parent_type = self.ProjectTree.GetPyData(parent)["type"]
       
  1928                 while parent_type != ITEM_POU:
       
  1929                     parent = self.ProjectTree.GetItemParent(parent)
       
  1930                     parent_type = self.ProjectTree.GetPyData(parent)["type"]
       
  1931                 self.Bind(wx.EVT_MENU, self.GenerateAddActionFunction(self.ProjectTree.GetItemText(parent)), id=new_id)
       
  1932             
       
  1933             elif name == "Resources":
       
  1934                 menu = wx.Menu(title='')
       
  1935                 new_id = wx.NewId()
       
  1936                 AppendMenu(menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Add Resource"))
       
  1937                 parent = self.ProjectTree.GetItemParent(item)
       
  1938                 parent_type = self.ProjectTree.GetPyData(parent)["type"]
       
  1939                 while parent_type not in [ITEM_CONFIGURATION, ITEM_PROJECT]:
       
  1940                     parent = self.ProjectTree.GetItemParent(parent)
       
  1941                     parent_type = self.ProjectTree.GetPyData(parent)["type"]
       
  1942                 if parent_type == ITEM_PROJECT:
       
  1943                     parent_name = None
       
  1944                 else:
       
  1945                     parent_name = self.ProjectTree.GetItemText(parent)
       
  1946                 self.Bind(wx.EVT_MENU, self.GenerateAddResourceFunction(parent_name), id=new_id)
       
  1947             
       
  1948         else:
       
  1949             if item_infos["type"] == ITEM_POU:
       
  1950                 menu = wx.Menu(title='')
       
  1951                 if self.Controler.GetPouBodyType(name) == "SFC":
       
  1952                     new_id = wx.NewId()
       
  1953                     AppendMenu(menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Add Transition"))
       
  1954                     self.Bind(wx.EVT_MENU, self.GenerateAddTransitionFunction(name), id=new_id)
       
  1955                     new_id = wx.NewId()
       
  1956                     AppendMenu(menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Add Action"))
       
  1957                     self.Bind(wx.EVT_MENU, self.GenerateAddActionFunction(name), id=new_id)
       
  1958                     menu.AppendSeparator()
       
  1959     
       
  1960                 new_id = wx.NewId()
       
  1961                 AppendMenu(menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Copy POU"))
       
  1962                 self.Bind(wx.EVT_MENU, self.OnCopyPou, id=new_id)
       
  1963     
       
  1964                 pou_type = self.Controler.GetPouType(name)
       
  1965                 if pou_type in ["function", "functionBlock"]:
       
  1966                     change_menu = wx.Menu(title='')
       
  1967                     if pou_type == "function":
       
  1968                         new_id = wx.NewId()
       
  1969                         AppendMenu(change_menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Function Block"))
       
  1970                         self.Bind(wx.EVT_MENU, self.GenerateChangePouTypeFunction(name, "functionBlock"), id=new_id)
       
  1971                     new_id = wx.NewId()
       
  1972                     AppendMenu(change_menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Program"))
       
  1973                     self.Bind(wx.EVT_MENU, self.GenerateChangePouTypeFunction(name, "program"), id=new_id)
       
  1974                     menu.AppendMenu(wx.NewId(), _("Change POU Type To"), change_menu)
       
  1975                 new_id = wx.NewId()
       
  1976                 AppendMenu(menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Rename"))
       
  1977                 self.Bind(wx.EVT_MENU, self.OnRenamePouMenu, id=new_id)
       
  1978             
       
  1979             elif item_infos["type"] == ITEM_CONFIGURATION:
       
  1980                 menu = wx.Menu(title='')
       
  1981                 new_id = wx.NewId()
       
  1982                 AppendMenu(menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Add Resource"))
       
  1983                 self.Bind(wx.EVT_MENU, self.GenerateAddResourceFunction(name), id=new_id)
       
  1984             
       
  1985             elif item_infos["type"] in [ITEM_DATATYPE, ITEM_TRANSITION, ITEM_ACTION, ITEM_RESOURCE]:
       
  1986                 menu = wx.Menu(title='')
       
  1987                 
       
  1988             if menu is not None:
       
  1989                 new_id = wx.NewId()
       
  1990                 AppendMenu(menu, help='', id=new_id, kind=wx.ITEM_NORMAL, text=_("Delete"))
       
  1991                 self.Bind(wx.EVT_MENU, self.OnDeleteMenu, id=new_id)
       
  1992         
       
  1993         if menu is not None:
       
  1994             self.PopupMenu(menu)
       
  1995             menu.Destroy()
       
  1996         
       
  1997         event.Skip()
       
  1998 
       
  1999 
       
  2000 #-------------------------------------------------------------------------------
       
  2001 #                         Instances Tree Management Functions
       
  2002 #-------------------------------------------------------------------------------
       
  2003 
       
  2004     def GetTreeImage(self, var_class):
       
  2005         return self.TreeImageDict[var_class]
       
  2006     
       
  2007     def RefreshPouInstanceVariablesPanel(self):
       
  2008         self.PouInstanceVariablesPanel.RefreshView()
       
  2009 
       
  2010     def OpenDebugViewer(self, instance_category, instance_path, instance_type):
       
  2011         openedidx = self.IsOpened(instance_path)
       
  2012         if openedidx is not None:
       
  2013             old_selected = self.TabsOpened.GetSelection()
       
  2014             if old_selected != openedidx:
       
  2015                 if old_selected >= 0:
       
  2016                     self.TabsOpened.GetPage(old_selected).ResetBuffer()
       
  2017                 self.TabsOpened.SetSelection(openedidx)
       
  2018         
       
  2019         elif instance_category in ITEMS_VARIABLE:
       
  2020             if self.Controler.IsOfType(instance_type, "ANY_NUM", True) or\
       
  2021                self.Controler.IsOfType(instance_type, "ANY_BIT", True):
       
  2022                 
       
  2023                 return self.OpenGraphicViewer(instance_path)
       
  2024         
       
  2025         else:
       
  2026             bodytype = self.Controler.GetEditedElementBodyType(instance_type, True)
       
  2027             new_window = None
       
  2028             if bodytype == "FBD":
       
  2029                 new_window = Viewer(self.TabsOpened, instance_type, self, self.Controler, True, instance_path)
       
  2030                 new_window.RefreshScaling(False)
       
  2031             elif bodytype == "LD":
       
  2032                 new_window = LD_Viewer(self.TabsOpened, instance_type, self, self.Controler, True, instance_path)
       
  2033                 new_window.RefreshScaling(False)
       
  2034             elif bodytype == "SFC":
       
  2035                 new_window = SFC_Viewer(self.TabsOpened, instance_type, self, self.Controler, True, instance_path)
       
  2036                 new_window.RefreshScaling(False)
       
  2037             else:
       
  2038                 new_window = TextViewer(self.TabsOpened, instance_type, self, self.Controler, True, instance_path)
       
  2039                 new_window.SetTextSyntax(bodytype)
       
  2040                 if bodytype == "IL":
       
  2041                     new_window.SetKeywords(IL_KEYWORDS)
       
  2042                 else:
       
  2043                     new_window.SetKeywords(ST_KEYWORDS)
       
  2044             if new_window is not None:
       
  2045                 project_infos = self.GetProjectConfiguration()
       
  2046                 if project_infos.has_key("editors_state"):
       
  2047                     state = project_infos["editors_state"].get(instance_path)
       
  2048                     if state is not None:
       
  2049                         wx.CallAfter(new_window.SetState, state)
       
  2050                 
       
  2051                 if instance_category in [ITEM_FUNCTIONBLOCK, ITEM_PROGRAM]:
       
  2052                     pou_type = self.Controler.GetEditedElementType(instance_type, True)[1].upper()
       
  2053                     icon = GetBitmap(pou_type, bodytype)
       
  2054                 elif instance_category == ITEM_TRANSITION:
       
  2055                     icon = GetBitmap("TRANSITION", bodytype)
       
  2056                 elif instance_category == ITEM_ACTION:
       
  2057                     icon = GetBitmap("ACTION", bodytype)
       
  2058                 new_window.SetIcon(icon)
       
  2059                 self.AddPage(new_window, "")
       
  2060                 new_window.RefreshView()
       
  2061                 new_window.SetFocus()
       
  2062                 self.RefreshPageTitles()
       
  2063             return new_window
       
  2064         
       
  2065         return None
       
  2066 
       
  2067     def OpenGraphicViewer(self, var_path):
       
  2068         new_window = GraphicViewer(self.TabsOpened, self, self.Controler, var_path)
       
  2069         new_window.SetIcon(GetBitmap("GRAPH"))
       
  2070         self.AddPage(new_window, "")
       
  2071         new_window.RefreshView()
       
  2072         new_window.SetFocus()
       
  2073         self.RefreshPageTitles()
       
  2074         return new_window
       
  2075 
       
  2076     def ResetGraphicViewers(self):
       
  2077         for i in xrange(self.TabsOpened.GetPageCount()):
       
  2078             editor = self.TabsOpened.GetPage(i)
       
  2079             if isinstance(editor, GraphicViewer):
       
  2080                 editor.ResetView()
       
  2081 
       
  2082     def CloseObsoleteDebugTabs(self):
       
  2083         if self.EnableDebug:
       
  2084             idxs = range(self.TabsOpened.GetPageCount())
       
  2085             idxs.reverse()
       
  2086             for idx in idxs:
       
  2087                 editor = self.TabsOpened.GetPage(idx)
       
  2088                 if editor.IsDebugging():
       
  2089                     instance_infos = self.Controler.GetInstanceInfos(editor.GetInstancePath(), self.EnableDebug)
       
  2090                     if instance_infos is None:
       
  2091                         self.TabsOpened.DeletePage(idx)
       
  2092                     elif isinstance(editor, GraphicViewer):
       
  2093                         editor.ResetView(True)
       
  2094                     else:
       
  2095                         editor.RefreshView()
       
  2096             self.DebugVariablePanel.UnregisterObsoleteData()
       
  2097     
       
  2098     def AddDebugVariable(self, iec_path, force=False):
       
  2099         if self.EnableDebug:
       
  2100             self.DebugVariablePanel.InsertValue(iec_path, force=force)
       
  2101             self.EnsureTabVisible(self.DebugVariablePanel)
       
  2102             
       
  2103 #-------------------------------------------------------------------------------
       
  2104 #                         Library Panel Management Function
       
  2105 #-------------------------------------------------------------------------------
       
  2106 
       
  2107     def RefreshLibraryPanel(self):
       
  2108         self.LibraryPanel.RefreshTree()
       
  2109         
       
  2110 #-------------------------------------------------------------------------------
       
  2111 #                          ToolBars Management Functions
       
  2112 #-------------------------------------------------------------------------------
       
  2113 
       
  2114     def AddToMenuToolBar(self, items):
       
  2115         MenuToolBar = self.Panes["MenuToolBar"]
       
  2116         if MenuToolBar.GetToolsCount() > 0:
       
  2117             MenuToolBar.AddSeparator()
       
  2118         for toolbar_item in items:
       
  2119             if toolbar_item is None:
       
  2120                 MenuToolBar.AddSeparator()
       
  2121             else:
       
  2122                 id, bitmap, help, callback = toolbar_item
       
  2123                 MenuToolBar.AddSimpleTool(id=id, shortHelpString=help, bitmap=GetBitmap(bitmap))
       
  2124                 if callback is not None:
       
  2125                     self.Bind(wx.EVT_TOOL, callback, id=id)
       
  2126         MenuToolBar.Realize()
       
  2127         self.AUIManager.GetPane("MenuToolBar").BestSize(MenuToolBar.GetBestSize())
       
  2128 
       
  2129     def ResetEditorToolBar(self):
       
  2130         EditorToolBar = self.Panes["EditorToolBar"]
       
  2131         
       
  2132         for item in self.CurrentEditorToolBar:
       
  2133             if wx.VERSION >= (2, 6, 0):
       
  2134                 self.Unbind(wx.EVT_MENU, id=item)
       
  2135             else:
       
  2136                 self.Disconnect(id=item, eventType=wx.wxEVT_COMMAND_MENU_SELECTED) 
       
  2137         
       
  2138             if EditorToolBar:
       
  2139                 EditorToolBar.DeleteTool(item)
       
  2140         
       
  2141         if EditorToolBar:
       
  2142             EditorToolBar.Realize()
       
  2143             self.AUIManager.GetPane("EditorToolBar").BestSize(EditorToolBar.GetBestSize())
       
  2144             self.AUIManager.GetPane("EditorToolBar").Hide()
       
  2145             self.AUIManager.Update()
       
  2146 
       
  2147     def RefreshEditorToolBar(self):
       
  2148         selected = self.TabsOpened.GetSelection()
       
  2149         menu = None
       
  2150         if selected != -1:
       
  2151             window = self.TabsOpened.GetPage(selected)
       
  2152             if isinstance(window, (Viewer, TextViewer, GraphicViewer)):
       
  2153                 if not window.IsDebugging():
       
  2154                     menu = self.Controler.GetEditedElementBodyType(window.GetTagName())
       
  2155                 else:
       
  2156                     menu = "debug"
       
  2157         if menu is not None and menu != self.CurrentMenu:
       
  2158             self.ResetEditorToolBar()
       
  2159             self.CurrentMenu = menu
       
  2160             self.CurrentEditorToolBar = []
       
  2161             EditorToolBar = self.Panes["EditorToolBar"]
       
  2162             if EditorToolBar:
       
  2163                 for radio, modes, id, method, picture, help in EditorToolBarItems[menu]:
       
  2164                     if modes & self.DrawingMode:
       
  2165                         if radio or self.DrawingMode == FREEDRAWING_MODE:
       
  2166                             EditorToolBar.AddRadioTool(id, GetBitmap(picture), wx.NullBitmap, help)
       
  2167                         else:
       
  2168                             EditorToolBar.AddSimpleTool(id, GetBitmap(picture), help)
       
  2169                         self.Bind(wx.EVT_MENU, getattr(self, method), id=id)
       
  2170                         self.CurrentEditorToolBar.append(id)
       
  2171                 EditorToolBar.Realize()
       
  2172                 self.AUIManager.GetPane("EditorToolBar").BestSize(EditorToolBar.GetBestSize())
       
  2173                 self.AUIManager.GetPane("EditorToolBar").Show()
       
  2174                 self.AUIManager.Update()
       
  2175         elif menu is None:
       
  2176             self.ResetEditorToolBar()
       
  2177             self.CurrentMenu = menu
       
  2178         self.ResetCurrentMode()
       
  2179 
       
  2180 
       
  2181 #-------------------------------------------------------------------------------
       
  2182 #                           EditorToolBar Items Functions
       
  2183 #-------------------------------------------------------------------------------
       
  2184 
       
  2185     def ResetCurrentMode(self):
       
  2186         selected = self.TabsOpened.GetSelection()
       
  2187         if selected != -1:
       
  2188             window = self.TabsOpened.GetPage(selected)
       
  2189             window.SetMode(MODE_SELECTION)
       
  2190         EditorToolBar = self.Panes["EditorToolBar"]
       
  2191         if EditorToolBar:
       
  2192             EditorToolBar.ToggleTool(ID_PLCOPENEDITOREDITORTOOLBARSELECTION, False)
       
  2193             EditorToolBar.ToggleTool(ID_PLCOPENEDITOREDITORTOOLBARSELECTION, True)
       
  2194         
       
  2195     def ResetToolToggle(self, id):
       
  2196         tool = self.Panes["EditorToolBar"].FindById(id)
       
  2197         tool.SetToggle(False)
       
  2198 
       
  2199     def OnSelectionTool(self, event):
       
  2200         selected = self.TabsOpened.GetSelection()
       
  2201         if selected != -1:
       
  2202             self.TabsOpened.GetPage(selected).SetMode(MODE_SELECTION)
       
  2203     
       
  2204     def OnMotionTool(self, event):
       
  2205         selected = self.TabsOpened.GetSelection()
       
  2206         if selected != -1:
       
  2207             self.TabsOpened.GetPage(selected).SetMode(MODE_MOTION)
       
  2208     
       
  2209     def OnCommentTool(self, event):
       
  2210         self.ResetToolToggle(ID_PLCOPENEDITOREDITORTOOLBARCOMMENT)
       
  2211         selected = self.TabsOpened.GetSelection()
       
  2212         if selected != -1:
       
  2213             self.TabsOpened.GetPage(selected).SetMode(MODE_COMMENT)
       
  2214     
       
  2215     def OnVariableTool(self, event):
       
  2216         self.ResetToolToggle(ID_PLCOPENEDITOREDITORTOOLBARVARIABLE)
       
  2217         selected = self.TabsOpened.GetSelection()
       
  2218         if selected != -1:
       
  2219             self.TabsOpened.GetPage(selected).SetMode(MODE_VARIABLE)
       
  2220     
       
  2221     def OnBlockTool(self, event):
       
  2222         self.ResetToolToggle(ID_PLCOPENEDITOREDITORTOOLBARBLOCK)
       
  2223         selected = self.TabsOpened.GetSelection()
       
  2224         if selected != -1:
       
  2225             self.TabsOpened.GetPage(selected).SetMode(MODE_BLOCK)
       
  2226         
       
  2227     def OnConnectionTool(self, event):
       
  2228         self.ResetToolToggle(ID_PLCOPENEDITOREDITORTOOLBARCONNECTION)
       
  2229         selected = self.TabsOpened.GetSelection()
       
  2230         if selected != -1:
       
  2231             self.TabsOpened.GetPage(selected).SetMode(MODE_CONNECTION)
       
  2232     
       
  2233     def OnPowerRailTool(self, event):
       
  2234         self.ResetToolToggle(ID_PLCOPENEDITOREDITORTOOLBARPOWERRAIL)
       
  2235         selected = self.TabsOpened.GetSelection()
       
  2236         if selected != -1:
       
  2237             self.TabsOpened.GetPage(selected).SetMode(MODE_POWERRAIL)
       
  2238     
       
  2239     def OnRungTool(self, event):
       
  2240         selected = self.TabsOpened.GetSelection()
       
  2241         if selected != -1:
       
  2242             self.TabsOpened.GetPage(selected).AddLadderRung()
       
  2243         event.Skip()
       
  2244     
       
  2245     def OnCoilTool(self, event):
       
  2246         self.ResetToolToggle(ID_PLCOPENEDITOREDITORTOOLBARCOIL)
       
  2247         selected = self.TabsOpened.GetSelection()
       
  2248         if selected != -1:
       
  2249             self.TabsOpened.GetPage(selected).SetMode(MODE_COIL)
       
  2250         event.Skip()
       
  2251     
       
  2252     def OnContactTool(self, event):
       
  2253         if self.DrawingMode == FREEDRAWING_MODE:
       
  2254             self.ResetToolToggle(ID_PLCOPENEDITOREDITORTOOLBARCONTACT)
       
  2255         selected = self.TabsOpened.GetSelection()
       
  2256         if selected != -1:
       
  2257             if self.DrawingMode == FREEDRAWING_MODE:
       
  2258                 self.TabsOpened.GetPage(selected).SetMode(MODE_CONTACT)
       
  2259             else:
       
  2260                 self.TabsOpened.GetPage(selected).AddLadderContact()
       
  2261     
       
  2262     def OnBranchTool(self, event): 
       
  2263         selected = self.TabsOpened.GetSelection()
       
  2264         if selected != -1:
       
  2265             self.TabsOpened.GetPage(selected).AddLadderBranch()
       
  2266     
       
  2267     def OnInitialStepTool(self, event):
       
  2268         self.ResetToolToggle(ID_PLCOPENEDITOREDITORTOOLBARINITIALSTEP)
       
  2269         selected = self.TabsOpened.GetSelection()
       
  2270         if selected != -1:
       
  2271             self.TabsOpened.GetPage(selected).SetMode(MODE_INITIALSTEP)
       
  2272     
       
  2273     def OnStepTool(self, event):
       
  2274         if self.GetDrawingMode() == FREEDRAWING_MODE:
       
  2275             self.ResetToolToggle(ID_PLCOPENEDITOREDITORTOOLBARSTEP)
       
  2276         selected = self.TabsOpened.GetSelection()
       
  2277         if selected != -1:
       
  2278             if self.GetDrawingMode() == FREEDRAWING_MODE:
       
  2279                 self.TabsOpened.GetPage(selected).SetMode(MODE_STEP)
       
  2280             else:
       
  2281                 self.TabsOpened.GetPage(selected).AddStep()
       
  2282     
       
  2283     def OnActionBlockTool(self, event):
       
  2284         if self.GetDrawingMode() == FREEDRAWING_MODE:
       
  2285             self.ResetToolToggle(ID_PLCOPENEDITOREDITORTOOLBARACTIONBLOCK)
       
  2286         selected = self.TabsOpened.GetSelection()
       
  2287         if selected != -1:
       
  2288             if self.GetDrawingMode() == FREEDRAWING_MODE:
       
  2289                 self.TabsOpened.GetPage(selected).SetMode(MODE_ACTION)
       
  2290             else:
       
  2291                 self.TabsOpened.GetPage(selected).AddStepAction()
       
  2292     
       
  2293     def OnTransitionTool(self, event):
       
  2294         self.ResetToolToggle(ID_PLCOPENEDITOREDITORTOOLBARTRANSITION)
       
  2295         selected = self.TabsOpened.GetSelection()
       
  2296         if selected != -1:
       
  2297             self.TabsOpened.GetPage(selected).SetMode(MODE_TRANSITION)
       
  2298     
       
  2299     def OnDivergenceTool(self, event):
       
  2300         if self.GetDrawingMode() == FREEDRAWING_MODE:
       
  2301             self.ResetToolToggle(ID_PLCOPENEDITOREDITORTOOLBARDIVERGENCE)
       
  2302         selected = self.TabsOpened.GetSelection()
       
  2303         if selected != -1:
       
  2304             if self.GetDrawingMode() == FREEDRAWING_MODE:
       
  2305                 self.TabsOpened.GetPage(selected).SetMode(MODE_DIVERGENCE)
       
  2306             else:
       
  2307                 self.TabsOpened.GetPage(selected).AddDivergence()
       
  2308     
       
  2309     def OnJumpTool(self, event):
       
  2310         if self.GetDrawingMode() == FREEDRAWING_MODE:
       
  2311             self.ResetToolToggle(ID_PLCOPENEDITOREDITORTOOLBARJUMP)
       
  2312         selected = self.TabsOpened.GetSelection()
       
  2313         if selected != -1:
       
  2314             if self.GetDrawingMode() == FREEDRAWING_MODE:
       
  2315                 self.TabsOpened.GetPage(selected).SetMode(MODE_JUMP)
       
  2316             else:
       
  2317                 self.TabsOpened.GetPage(selected).AddJump()
       
  2318     
       
  2319 
       
  2320 #-------------------------------------------------------------------------------
       
  2321 #                         Add Project Elements Functions
       
  2322 #-------------------------------------------------------------------------------
       
  2323 
       
  2324     def OnAddDataTypeMenu(self, event):
       
  2325         tagname = self.Controler.ProjectAddDataType()
       
  2326         if tagname is not None:
       
  2327             self._Refresh(TITLE, FILEMENU, EDITMENU, PROJECTTREE)
       
  2328             self.EditProjectElement(ITEM_DATATYPE, tagname)
       
  2329         
       
  2330     def GenerateAddPouFunction(self, pou_type):
       
  2331         def OnAddPouMenu(event):
       
  2332             dialog = PouDialog(self, pou_type)
       
  2333             dialog.SetPouNames(self.Controler.GetProjectPouNames())
       
  2334             dialog.SetPouElementNames(self.Controler.GetProjectPouVariables())
       
  2335             dialog.SetValues({"pouName": self.Controler.GenerateNewName(None, None, "%s%%d" % pou_type)})
       
  2336             if dialog.ShowModal() == wx.ID_OK:
       
  2337                 values = dialog.GetValues()
       
  2338                 tagname = self.Controler.ProjectAddPou(values["pouName"], values["pouType"], values["language"])
       
  2339                 if tagname is not None:
       
  2340                     self._Refresh(TITLE, FILEMENU, EDITMENU, PROJECTTREE, LIBRARYTREE)
       
  2341                     self.EditProjectElement(ITEM_POU, tagname)
       
  2342             dialog.Destroy()
       
  2343         return OnAddPouMenu
       
  2344 
       
  2345     def GenerateAddTransitionFunction(self, pou_name):
       
  2346         def OnAddTransitionMenu(event):
       
  2347             dialog = PouTransitionDialog(self)
       
  2348             dialog.SetPouNames(self.Controler.GetProjectPouNames())
       
  2349             dialog.SetPouElementNames(self.Controler.GetProjectPouVariables(pou_name))
       
  2350             dialog.SetValues({"transitionName": self.Controler.GenerateNewName(None, None, "transition%d")})
       
  2351             if dialog.ShowModal() == wx.ID_OK: 
       
  2352                 values = dialog.GetValues()
       
  2353                 tagname = self.Controler.ProjectAddPouTransition(pou_name, values["transitionName"], values["language"])
       
  2354                 if tagname is not None:
       
  2355                     self._Refresh(TITLE, FILEMENU, EDITMENU, PROJECTTREE)
       
  2356                     self.EditProjectElement(ITEM_TRANSITION, tagname)
       
  2357             dialog.Destroy()
       
  2358         return OnAddTransitionMenu
       
  2359 
       
  2360     def GenerateAddActionFunction(self, pou_name):
       
  2361         def OnAddActionMenu(event):
       
  2362             dialog = PouActionDialog(self)
       
  2363             dialog.SetPouNames(self.Controler.GetProjectPouNames())
       
  2364             dialog.SetPouElementNames(self.Controler.GetProjectPouVariables(pou_name))
       
  2365             dialog.SetValues({"actionName": self.Controler.GenerateNewName(None, None, "action%d")})
       
  2366             if dialog.ShowModal() == wx.ID_OK:
       
  2367                 values = dialog.GetValues()
       
  2368                 tagname = self.Controler.ProjectAddPouAction(pou_name, values["actionName"], values["language"])
       
  2369                 if tagname is not None:
       
  2370                     self._Refresh(TITLE, FILEMENU, EDITMENU, PROJECTTREE)
       
  2371                     self.EditProjectElement(ITEM_ACTION, tagname)
       
  2372             dialog.Destroy()
       
  2373         return OnAddActionMenu
       
  2374 
       
  2375     def OnAddConfigurationMenu(self, event):
       
  2376         tagname = self.Controler.ProjectAddConfiguration()
       
  2377         if tagname is not None:
       
  2378             self._Refresh(TITLE, FILEMENU, EDITMENU, PROJECTTREE, POUINSTANCEVARIABLESPANEL)
       
  2379             self.EditProjectElement(ITEM_CONFIGURATION, tagname)
       
  2380         dialog.Destroy()
       
  2381 
       
  2382     def GenerateAddResourceFunction(self, config_name):
       
  2383         def OnAddResourceMenu(event):
       
  2384             tagname = self.Controler.ProjectAddConfigurationResource(config_name)
       
  2385             if tagname is not None:
       
  2386                 self._Refresh(TITLE, FILEMENU, EDITMENU, PROJECTTREE, POUINSTANCEVARIABLESPANEL)
       
  2387                 self.EditProjectElement(ITEM_RESOURCE, tagname)
       
  2388         return OnAddResourceMenu
       
  2389 
       
  2390     def GenerateChangePouTypeFunction(self, name, new_type):
       
  2391         def OnChangePouTypeMenu(event):
       
  2392             selected = self.ProjectTree.GetSelection()
       
  2393             if self.ProjectTree.GetPyData(selected)["type"] == ITEM_POU: 
       
  2394                 self.Controler.ProjectChangePouType(name, new_type)
       
  2395                 self._Refresh(TITLE, EDITORTOOLBAR, FILEMENU, EDITMENU, PROJECTTREE, LIBRARYTREE)
       
  2396         return OnChangePouTypeMenu
       
  2397 
       
  2398     def OnCopyPou(self, event):
       
  2399         selected = self.ProjectTree.GetSelection()
       
  2400         pou_name = self.ProjectTree.GetItemText(selected)
       
  2401         
       
  2402         pou_xml = self.Controler.GetPouXml(pou_name)
       
  2403         if pou_xml is not None:
       
  2404             self.SetCopyBuffer(pou_xml)
       
  2405             self._Refresh(EDITMENU)
       
  2406 
       
  2407     def OnPastePou(self, event):
       
  2408         selected = self.ProjectTree.GetSelection()
       
  2409         
       
  2410         if self.ProjectTree.GetPyData(selected)["type"] != ITEM_PROJECT: 
       
  2411             pou_type = self.ProjectTree.GetItemText(selected)
       
  2412             pou_type = UNEDITABLE_NAMES_DICT[pou_type] # one of 'Functions', 'Function Blocks' or 'Programs'
       
  2413             pou_type = {'Functions': 'function', 'Function Blocks': 'functionBlock', 'Programs': 'program'}[pou_type]
       
  2414         else:
       
  2415             pou_type = None
       
  2416         
       
  2417         pou_xml = self.GetCopyBuffer()
       
  2418 
       
  2419         result = self.Controler.PastePou(pou_type, pou_xml)
       
  2420 
       
  2421         if not isinstance(result, TupleType):
       
  2422             message = wx.MessageDialog(self, result, _("Error"), wx.OK|wx.ICON_ERROR)
       
  2423             message.ShowModal()
       
  2424             message.Destroy()
       
  2425         else:
       
  2426             self._Refresh(TITLE, EDITORTOOLBAR, FILEMENU, EDITMENU, PROJECTTREE, LIBRARYTREE)
       
  2427             self.EditProjectElement(ITEM_POU, result[0])
       
  2428 
       
  2429 #-------------------------------------------------------------------------------
       
  2430 #                        Remove Project Elements Functions
       
  2431 #-------------------------------------------------------------------------------
       
  2432 
       
  2433     def OnRemoveDataTypeMenu(self, event):
       
  2434         selected = self.ProjectTree.GetSelection()
       
  2435         if self.ProjectTree.GetPyData(selected)["type"] == ITEM_DATATYPE:
       
  2436             name = self.ProjectTree.GetItemText(selected)
       
  2437             if not self.Controler.DataTypeIsUsed(name):
       
  2438                 self.Controler.ProjectRemoveDataType(name)
       
  2439                 tagname = self.Controler.ComputeDataTypeName(name)
       
  2440                 idx = self.IsOpened(tagname)
       
  2441                 if idx is not None:
       
  2442                     self.TabsOpened.DeletePage(idx)
       
  2443                 self._Refresh(TITLE, EDITORTOOLBAR, FILEMENU, EDITMENU, PROJECTTREE)
       
  2444             else:
       
  2445                 self.ShowErrorMessage(_("\"%s\" is used by one or more POUs. It can't be removed!"))
       
  2446 
       
  2447     def OnRenamePouMenu(self, event):
       
  2448         selected = self.ProjectTree.GetSelection()
       
  2449         if self.ProjectTree.GetPyData(selected)["type"] == ITEM_POU: 
       
  2450             wx.CallAfter(self.ProjectTree.EditLabel, selected)
       
  2451 
       
  2452     def OnRemovePouMenu(self, event):
       
  2453         selected = self.ProjectTree.GetSelection()
       
  2454         if self.ProjectTree.GetPyData(selected)["type"] == ITEM_POU:
       
  2455             name = self.ProjectTree.GetItemText(selected)
       
  2456             if not self.Controler.PouIsUsed(name):
       
  2457                 self.Controler.ProjectRemovePou(name)
       
  2458                 tagname = self.Controler.ComputePouName(name)
       
  2459                 idx = self.IsOpened(tagname)
       
  2460                 if idx is not None:
       
  2461                     self.TabsOpened.DeletePage(idx)
       
  2462                 self._Refresh(TITLE, EDITORTOOLBAR, FILEMENU, EDITMENU, PROJECTTREE, POUINSTANCEVARIABLESPANEL, LIBRARYTREE)
       
  2463             else:
       
  2464                 self.ShowErrorMessage(_("\"%s\" is used by one or more POUs. It can't be removed!"))
       
  2465 
       
  2466     def OnRemoveTransitionMenu(self, event):
       
  2467         selected = self.ProjectTree.GetSelection()
       
  2468         item_infos = self.ProjectTree.GetPyData(selected)
       
  2469         if item_infos["type"] == ITEM_TRANSITION: 
       
  2470             transition = self.ProjectTree.GetItemText(selected)
       
  2471             pou_name = item_infos["tagname"].split("::")[1]
       
  2472             self.Controler.ProjectRemovePouTransition(pou_name, transition)
       
  2473             tagname = self.Controler.ComputePouTransitionName(pou_name, transition)
       
  2474             idx = self.IsOpened(tagname)
       
  2475             if idx is not None:
       
  2476                 self.TabsOpened.DeletePage(idx)
       
  2477             self._Refresh(TITLE, FILEMENU, EDITMENU, PROJECTTREE)
       
  2478 
       
  2479     def OnRemoveActionMenu(self, event):
       
  2480         selected = self.ProjectTree.GetSelection()
       
  2481         item_infos = self.ProjectTree.GetPyData(selected)
       
  2482         if item_infos["type"] == ITEM_ACTION: 
       
  2483             action = self.ProjectTree.GetItemText(selected)
       
  2484             pou_name = item_infos["tagname"].split("::")[1]
       
  2485             self.Controler.ProjectRemovePouAction(pou_name, action)
       
  2486             tagname = self.Controler.ComputePouActionName(pou_name, action)
       
  2487             idx = self.IsOpened(tagname)
       
  2488             if idx is not None:
       
  2489                 self.TabsOpened.DeletePage(idx)
       
  2490             self._Refresh(TITLE, FILEMENU, EDITMENU, PROJECTTREE)
       
  2491 
       
  2492     def OnRemoveConfigurationMenu(self, event):
       
  2493         selected = self.ProjectTree.GetSelection()
       
  2494         if self.ProjectTree.GetPyData(selected)["type"] == ITEM_CONFIGURATION: 
       
  2495             name = self.ProjectTree.GetItemText(selected)
       
  2496             self.Controler.ProjectRemoveConfiguration(name)
       
  2497             tagname = self.Controler.ComputeConfigurationName(name)
       
  2498             idx = self.IsOpened(tagname)
       
  2499             if idx is not None:
       
  2500                 self.TabsOpened.DeletePage(idx)
       
  2501             self._Refresh(TITLE, FILEMENU, EDITMENU, PROJECTTREE, POUINSTANCEVARIABLESPANEL)
       
  2502 
       
  2503     def OnRemoveResourceMenu(self, event):
       
  2504         selected = self.ProjectTree.GetSelection()
       
  2505         item_infos = self.ProjectTree.GetPyData(selected)
       
  2506         if item_infos["type"] == ITEM_RESOURCE:
       
  2507             resource = self.ProjectTree.GetItemText(selected)
       
  2508             config_name = item_infos["tagname"].split("::")[1]
       
  2509             self.Controler.ProjectRemoveConfigurationResource(config_name, resource)
       
  2510             tagname = self.Controler.ComputeConfigurationResourceName(config_name, selected)
       
  2511             idx = self.IsOpened(tagname)
       
  2512             if idx is not None:
       
  2513                 self.TabsOpened.DeletePage(idx)
       
  2514             self._Refresh(TITLE, FILEMENU, EDITMENU, PROJECTTREE, POUINSTANCEVARIABLESPANEL)
       
  2515 
       
  2516 #-------------------------------------------------------------------------------
       
  2517 #                        Highlights showing functions
       
  2518 #-------------------------------------------------------------------------------
       
  2519 
       
  2520     def ShowHighlight(self, infos, start, end, highlight_type):
       
  2521         self.SelectProjectTreeItem(infos[0])
       
  2522         if infos[1] == "name":
       
  2523             self.Highlights[infos[0]] = highlight_type
       
  2524             self.RefreshProjectTree()
       
  2525             self.ProjectTree.Unselect()
       
  2526         else:
       
  2527             self.EditProjectElement(self.Controler.GetElementType(infos[0]), infos[0])
       
  2528             selected = self.TabsOpened.GetSelection()
       
  2529             if selected != -1:
       
  2530                 viewer = self.TabsOpened.GetPage(selected)
       
  2531                 viewer.AddHighlight(infos[1:], start, end, highlight_type)
       
  2532 
       
  2533     def ShowError(self, infos, start, end):
       
  2534         self.ShowHighlight(infos, start, end, ERROR_HIGHLIGHT)
       
  2535 
       
  2536     def ShowSearchResult(self, infos, start, end):
       
  2537         self.ShowHighlight(infos, start, end, SEARCH_RESULT_HIGHLIGHT)
       
  2538 
       
  2539     def ClearHighlights(self, highlight_type=None):
       
  2540         if highlight_type is None:
       
  2541             self.Highlights = {}
       
  2542         else:
       
  2543             self.Highlights = dict([(name, highlight) for name, highlight in self.Highlights.iteritems() if highlight != highlight_type])
       
  2544         self.RefreshProjectTree()
       
  2545         for i in xrange(self.TabsOpened.GetPageCount()):
       
  2546             viewer = self.TabsOpened.GetPage(i)
       
  2547             viewer.ClearHighlights(highlight_type)
       
  2548 
       
  2549     def ClearErrors(self):
       
  2550         self.ClearHighlights(ERROR_HIGHLIGHT)
       
  2551 
       
  2552     def ClearSearchResults(self):
       
  2553         self.ClearHighlights(SEARCH_RESULT_HIGHLIGHT)