]>
git.saurik.com Git - wxWidgets.git/blob - wxPython/samples/ide/activegrid/tool/FindInDirService.py 
   1  #----------------------------------------------------------------------------    2  # Name:         IDEFindService.py    3  # Purpose:      Find Service for pydocview    9  # Copyright:    (c) 2004-2005 ActiveGrid, Inc.   10  # License:      wxWindows License   11  #----------------------------------------------------------------------------   16  from  os
. path 
import  join
  25  #----------------------------------------------------------------------------   27  #----------------------------------------------------------------------------   28  FILENAME_MARKER 
=  _ ( "Found in file: " )   29  PROJECT_MARKER 
=  _ ( "Searching project: " )   30  FIND_MATCHDIR 
=  "FindMatchDir"   31  FIND_MATCHDIRSUBFOLDERS 
=  "FindMatchDirSubfolders"   37  class  FindInDirService ( FindService
. FindService
):   39      #----------------------------------------------------------------------------   41      #----------------------------------------------------------------------------   42      FINDALL_ID 
=  wx
. NewId ()          # for bringing up Find All dialog box   43      FINDDIR_ID 
=  wx
. NewId ()          # for bringing up Find Dir dialog box   46      def  InstallControls ( self
,  frame
,  menuBar 
=  None ,  toolBar 
=  None ,  statusBar 
=  None ,  document 
=  None ):   47          FindService
. FindService
. InstallControls ( self
,  frame
,  menuBar
,  toolBar
,  statusBar
,  document
)   49          editMenu 
=  menuBar
. GetMenu ( menuBar
. FindMenu ( _ ( "&Edit" )))   50          wx
. EVT_MENU ( frame
,  FindInDirService
. FINDALL_ID
,  self
. ProcessEvent
)   51          wx
. EVT_UPDATE_UI ( frame
,  FindInDirService
. FINDALL_ID
,  self
. ProcessUpdateUIEvent
)   52          editMenu
. Append ( FindInDirService
. FINDALL_ID
,  _ ( "Find in Project... \t Ctrl+Shift+F" ),  _ ( "Searches for the specified text in all the files in the project" ))   53          wx
. EVT_MENU ( frame
,  FindInDirService
. FINDDIR_ID
,  self
. ProcessEvent
)   54          wx
. EVT_UPDATE_UI ( frame
,  FindInDirService
. FINDDIR_ID
,  self
. ProcessUpdateUIEvent
)   55          editMenu
. Append ( FindInDirService
. FINDDIR_ID
,  _ ( "Find in Directory..." ),  _ ( "Searches for the specified text in all the files in the directory" ))   58      def  ProcessEvent ( self
,  event
):   60          if  id  ==  FindInDirService
. FINDALL_ID
:   61              view 
=  wx
. GetApp (). GetDocumentManager (). GetCurrentView ()   62              if  hasattr ( view
,  "GetCtrl" )  and  view
. GetCtrl ()  and  hasattr ( view
. GetCtrl (),  "GetSelectedText" ):   63                  self
. ShowFindAllDialog ( view
. GetCtrl (). GetSelectedText ())   65                  self
. ShowFindAllDialog ()   67          elif  id  ==  FindInDirService
. FINDDIR_ID
:   68              view 
=  wx
. GetApp (). GetDocumentManager (). GetCurrentView ()   69              if  hasattr ( view
,  "GetCtrl" )  and  view
. GetCtrl ()  and  hasattr ( view
. GetCtrl (),  "GetSelectedText" ):   70                  self
. ShowFindDirDialog ( view
. GetCtrl (). GetSelectedText ())   72                  self
. ShowFindDirDialog ()   75              return  FindService
. FindService
. ProcessEvent ( self
,  event
)   78      def  ProcessUpdateUIEvent ( self
,  event
):   80          if  id  ==  FindInDirService
. FINDALL_ID
:   81              projectService 
=  wx
. GetApp (). GetService ( ProjectEditor
. ProjectService
)   82              if  projectService
. GetFilesFromCurrentProject ():   87          elif  id  ==  FindInDirService
. FINDDIR_ID
:   90              return  FindService
. FindService
. ProcessUpdateUIEvent ( self
,  event
)   93      def  ShowFindDirDialog ( self
,  findString
= None ):   94          config 
=  wx
. ConfigBase_Get ()   96          frame 
=  wx
. Dialog ( wx
. GetApp (). GetTopWindow (), - 1 ,  _ ( "Find in Directory" ),  size
= ( 320 , 200 ))   97          borderSizer 
=  wx
. BoxSizer ( wx
. HORIZONTAL
)   99          contentSizer 
=  wx
. BoxSizer ( wx
. VERTICAL
)  100          lineSizer 
=  wx
. BoxSizer ( wx
. HORIZONTAL
)  101          lineSizer
. Add ( wx
. StaticText ( frame
, - 1 ,  _ ( "Directory:" )),  0 ,  wx
. ALIGN_CENTER | wx
. RIGHT
,  HALF_SPACE
)  102          dirCtrl 
=  wx
. TextCtrl ( frame
, - 1 ,  config
. Read ( FIND_MATCHDIR
,  "" ),  size
=( 200 ,- 1 ))  103          dirCtrl
. SetToolTipString ( dirCtrl
. GetValue ())  104          lineSizer
. Add ( dirCtrl
,  0 ,  wx
. LEFT
,  HALF_SPACE
)  105          findDirButton 
=  wx
. Button ( frame
, - 1 ,  _ ( "Browse..." ))  106          lineSizer
. Add ( findDirButton
,  0 ,  wx
. LEFT
,  HALF_SPACE
)  107          contentSizer
. Add ( lineSizer
,  0 ,  wx
. BOTTOM
,  SPACE
)  109          def  OnBrowseButton ( event
):  110              dlg 
=  wx
. DirDialog ( frame
,  _ ( "Choose a directory:" ),  style
= wx
. DD_DEFAULT_STYLE
)  111              dir  =  dirCtrl
. GetValue ()  115              if  dlg
. ShowModal () ==  wx
. ID_OK
:  116                  dirCtrl
. SetValue ( dlg
. GetPath ())  117                  dirCtrl
. SetToolTipString ( dirCtrl
. GetValue ())  118                  dirCtrl
. SetInsertionPointEnd ()  120          wx
. EVT_BUTTON ( findDirButton
, - 1 ,  OnBrowseButton
)  122          subfolderCtrl 
=  wx
. CheckBox ( frame
, - 1 ,  _ ( "Search in subdirectories" ))  123          subfolderCtrl
. SetValue ( config
. ReadInt ( FIND_MATCHDIRSUBFOLDERS
,  True ))  124          contentSizer
. Add ( subfolderCtrl
,  0 ,  wx
. BOTTOM
,  SPACE
)  126          lineSizer 
=  wx
. BoxSizer ( wx
. VERTICAL
)     # let the line expand horizontally without vertical expansion  127          lineSizer
. Add ( wx
. StaticLine ( frame
, - 1 ,  size 
= ( 10 ,- 1 )),  0 ,  flag
= wx
. EXPAND
)  128          contentSizer
. Add ( lineSizer
,  flag
= wx
. EXPAND|wx
. ALIGN_CENTER_VERTICAL|wx
. BOTTOM
,  border
= HALF_SPACE
)  130          if  wx
. Platform 
==  "__WXMAC__" :  131              contentSizer
. Add ((- 1 ,  10 ),  0 ,  wx
. EXPAND
)  133          lineSizer 
=  wx
. BoxSizer ( wx
. HORIZONTAL
)  134          lineSizer
. Add ( wx
. StaticText ( frame
, - 1 ,  _ ( "Find what:" )),  0 ,  wx
. ALIGN_CENTER | wx
. RIGHT
,  HALF_SPACE
)  136              findString 
=  config
. Read ( FindService
. FIND_MATCHPATTERN
,  "" )  137          findCtrl 
=  wx
. TextCtrl ( frame
, - 1 ,  findString
,  size
=( 200 ,- 1 ))  139          findCtrl
. SetSelection ( 0 ,- 1 )  140          lineSizer
. Add ( findCtrl
,  0 ,  wx
. LEFT
,  HALF_SPACE
)  141          contentSizer
. Add ( lineSizer
,  0 ,  wx
. BOTTOM
,  SPACE
)  142          wholeWordCtrl 
=  wx
. CheckBox ( frame
, - 1 ,  _ ( "Match whole word only" ))  143          wholeWordCtrl
. SetValue ( config
. ReadInt ( FindService
. FIND_MATCHWHOLEWORD
,  False ))  144          matchCaseCtrl 
=  wx
. CheckBox ( frame
, - 1 ,  _ ( "Match case" ))  145          matchCaseCtrl
. SetValue ( config
. ReadInt ( FindService
. FIND_MATCHCASE
,  False ))  146          regExprCtrl 
=  wx
. CheckBox ( frame
, - 1 ,  _ ( "Regular expression" ))  147          regExprCtrl
. SetValue ( config
. ReadInt ( FindService
. FIND_MATCHREGEXPR
,  False ))  148          contentSizer
. Add ( wholeWordCtrl
,  0 ,  wx
. BOTTOM
,  SPACE
)  149          contentSizer
. Add ( matchCaseCtrl
,  0 ,  wx
. BOTTOM
,  SPACE
)  150          contentSizer
. Add ( regExprCtrl
,  0 ,  wx
. BOTTOM
,  SPACE
)  151          borderSizer
. Add ( contentSizer
,  0 ,  wx
. TOP | wx
. BOTTOM | wx
. LEFT
,  SPACE
)  153          buttonSizer 
=  wx
. BoxSizer ( wx
. VERTICAL
)  154          findBtn 
=  wx
. Button ( frame
,  wx
. ID_OK
,  _ ( "Find" ))  156          BTM_SPACE 
=  HALF_SPACE
 157          if  wx
. Platform 
==  "__WXMAC__" :  159          buttonSizer
. Add ( findBtn
,  0 ,  wx
. BOTTOM
,  BTM_SPACE
)  160          buttonSizer
. Add ( wx
. Button ( frame
,  wx
. ID_CANCEL
),  0 )  161          borderSizer
. Add ( buttonSizer
,  0 ,  wx
. ALL
,  SPACE
)  163          frame
. SetSizer ( borderSizer
)  166          frame
. CenterOnParent ()  167          status 
=  frame
. ShowModal ()  170          while  status 
==  wx
. ID_OK 
and not  passedCheck
:  171              if not  os
. path
. exists ( dirCtrl
. GetValue ()):  172                  dlg 
=  wx
. MessageDialog ( frame
,  173                                         _ ( "' %s ' does not exist." ) %  dirCtrl
. GetValue (),  174                                         _ ( "Find in Directory" ),  175                                         wx
. OK | wx
. ICON_EXCLAMATION
 181                  status 
=  frame
. ShowModal ()  182              elif  len ( findCtrl
. GetValue ()) ==  0 :  183                  dlg 
=  wx
. MessageDialog ( frame
,  184                                         _ ( "'Find what:' cannot be empty." ),  185                                         _ ( "Find in Directory" ),  186                                         wx
. OK | wx
. ICON_EXCLAMATION
 192                  status 
=  frame
. ShowModal ()  197          # save user choice state for this and other Find Dialog Boxes  198          dirString 
=  dirCtrl
. GetValue ()  199          searchSubfolders 
=  subfolderCtrl
. IsChecked ()  200          self
. SaveFindDirConfig ( dirString
,  searchSubfolders
)  202          findString 
=  findCtrl
. GetValue ()  203          matchCase 
=  matchCaseCtrl
. IsChecked ()  204          wholeWord 
=  wholeWordCtrl
. IsChecked ()  205          regExpr 
=  regExprCtrl
. IsChecked ()  206          self
. SaveFindConfig ( findString
,  wholeWord
,  matchCase
,  regExpr
)  209          if  status 
==  wx
. ID_OK
:              210              messageService 
=  wx
. GetApp (). GetService ( MessageService
. MessageService
)  211              messageService
. ShowWindow ()  213              view 
=  messageService
. GetView ()  215                  wx
. GetApp (). GetTopWindow (). SetCursor ( wx
. StockCursor ( wx
. CURSOR_WAIT
))  217                  view
. SetCallback ( self
. OnJumpToFoundLine
)  219                  view
. AddLines ( _ ( "Searching for ' %s ' in ' %s ' \n\n " ) % ( findString
,  dirString
))  221                  if  os
. path
. isfile ( dirString
):  223                          docFile 
=  file ( dirString
,  'r' )  225                          needToDisplayFilename 
=  True  226                          line 
=  docFile
. readline ()  228                              count
,  foundStart
,  foundEnd
,  newText 
=  self
. DoFind ( findString
,  None ,  line
,  0 ,  0 ,  True ,  matchCase
,  wholeWord
,  regExpr
)  230                                  if  needToDisplayFilename
:  231                                      view
. AddLines ( FILENAME_MARKER 
+  dirString 
+  " \n " )  232                                      needToDisplayFilename 
=  False  233                                  line 
=  repr ( lineNum
). zfill ( 4 ) +  ":"  +  line
 235                              line 
=  docFile
. readline ()  237                          if not  needToDisplayFilename
:  239                      except  IOError , ( code
,  message
):  240                          print  _ ( "Warning, unable to read file: ' %s '.   %s " ) % ( dirString
,  message
)  242                      # do search in files on disk  243                      for  root
,  dirs
,  files 
in  os
. walk ( dirString
):  244                          if not  searchSubfolders 
and  root 
!=  dirString
:  248                              filename 
=  os
. path
. join ( root
,  name
)  250                                  docFile 
=  file ( filename
,  'r' )  251                              except  IOError , ( code
,  message
):  252                                  print  _ ( "Warning, unable to read file: ' %s '.   %s " ) % ( filename
,  message
)  256                              needToDisplayFilename 
=  True  257                              line 
=  docFile
. readline ()  259                                  count
,  foundStart
,  foundEnd
,  newText 
=  self
. DoFind ( findString
,  None ,  line
,  0 ,  0 ,  True ,  matchCase
,  wholeWord
,  regExpr
)  261                                      if  needToDisplayFilename
:  262                                          view
. AddLines ( FILENAME_MARKER 
+  filename 
+  " \n " )  263                                          needToDisplayFilename 
=  False  264                                      line 
=  repr ( lineNum
). zfill ( 4 ) +  ":"  +  line
 266                                  line 
=  docFile
. readline ()  268                              if not  needToDisplayFilename
:  271                  view
. AddLines ( _ ( "Search completed." ))  272                  wx
. GetApp (). GetTopWindow (). SetCursor ( wx
. StockCursor ( wx
. CURSOR_DEFAULT
))  279      def  SaveFindDirConfig ( self
,  dirString
,  searchSubfolders
):  280          """ Save search dir patterns and flags to registry.  282              dirString = search directory  283              searchSubfolders = Search subfolders  285          config 
=  wx
. ConfigBase_Get ()  286          config
. Write ( FIND_MATCHDIR
,  dirString
)  287          config
. WriteInt ( FIND_MATCHDIRSUBFOLDERS
,  searchSubfolders
)  290      def  ShowFindAllDialog ( self
,  findString
= None ):  291          config 
=  wx
. ConfigBase_Get ()  293          frame 
=  wx
. Dialog ( wx
. GetApp (). GetTopWindow (), - 1 ,  _ ( "Find in Project" ),  size
= ( 320 , 200 ))  294          borderSizer 
=  wx
. BoxSizer ( wx
. HORIZONTAL
)  296          contentSizer 
=  wx
. BoxSizer ( wx
. VERTICAL
)  297          lineSizer 
=  wx
. BoxSizer ( wx
. HORIZONTAL
)  298          lineSizer
. Add ( wx
. StaticText ( frame
, - 1 ,  _ ( "Find what:" )),  0 ,  wx
. ALIGN_CENTER | wx
. RIGHT
,  HALF_SPACE
)  300              findString 
=  config
. Read ( FindService
. FIND_MATCHPATTERN
,  "" )  301          findCtrl 
=  wx
. TextCtrl ( frame
, - 1 ,  findString
,  size
=( 200 ,- 1 ))  302          lineSizer
. Add ( findCtrl
,  0 ,  wx
. LEFT
,  HALF_SPACE
)  303          contentSizer
. Add ( lineSizer
,  0 ,  wx
. BOTTOM
,  SPACE
)  304          wholeWordCtrl 
=  wx
. CheckBox ( frame
, - 1 ,  _ ( "Match whole word only" ))  305          wholeWordCtrl
. SetValue ( config
. ReadInt ( FindService
. FIND_MATCHWHOLEWORD
,  False ))  306          matchCaseCtrl 
=  wx
. CheckBox ( frame
, - 1 ,  _ ( "Match case" ))  307          matchCaseCtrl
. SetValue ( config
. ReadInt ( FindService
. FIND_MATCHCASE
,  False ))  308          regExprCtrl 
=  wx
. CheckBox ( frame
, - 1 ,  _ ( "Regular expression" ))  309          regExprCtrl
. SetValue ( config
. ReadInt ( FindService
. FIND_MATCHREGEXPR
,  False ))  310          contentSizer
. Add ( wholeWordCtrl
,  0 ,  wx
. BOTTOM
,  SPACE
)  311          contentSizer
. Add ( matchCaseCtrl
,  0 ,  wx
. BOTTOM
,  SPACE
)  312          contentSizer
. Add ( regExprCtrl
,  0 ,  wx
. BOTTOM
,  SPACE
)  313          borderSizer
. Add ( contentSizer
,  0 ,  wx
. TOP | wx
. BOTTOM | wx
. LEFT
,  SPACE
)  315          buttonSizer 
=  wx
. BoxSizer ( wx
. VERTICAL
)  316          findBtn 
=  wx
. Button ( frame
,  wx
. ID_OK
,  _ ( "Find" ))  318          BTM_SPACE 
=  HALF_SPACE
 319          if  wx
. Platform 
==  "__WXMAC__" :  321          buttonSizer
. Add ( findBtn
,  0 ,  wx
. BOTTOM
,  BTM_SPACE
)  322          buttonSizer
. Add ( wx
. Button ( frame
,  wx
. ID_CANCEL
),  0 )  323          borderSizer
. Add ( buttonSizer
,  0 ,  wx
. ALL
,  SPACE
)  325          frame
. SetSizer ( borderSizer
)  328          frame
. CenterOnParent ()  329          status 
=  frame
. ShowModal ()  331          # save user choice state for this and other Find Dialog Boxes  332          findString 
=  findCtrl
. GetValue ()  333          matchCase 
=  matchCaseCtrl
. IsChecked ()  334          wholeWord 
=  wholeWordCtrl
. IsChecked ()  335          regExpr 
=  regExprCtrl
. IsChecked ()  336          self
. SaveFindConfig ( findString
,  wholeWord
,  matchCase
,  regExpr
)  339          if  status 
==  wx
. ID_OK
:  340              messageService 
=  wx
. GetApp (). GetService ( MessageService
. MessageService
)  341              messageService
. ShowWindow ()  343              view 
=  messageService
. GetView ()  346                  view
. SetCallback ( self
. OnJumpToFoundLine
)  348                  projectService 
=  wx
. GetApp (). GetService ( ProjectEditor
. ProjectService
)  349                  projectFilenames 
=  projectService
. GetFilesFromCurrentProject ()  351                  projView 
=  projectService
. GetView ()  353                      projName 
=  wx
. lib
. docview
. FileNameFromPath ( projView
. GetDocument (). GetFilename ())  354                      view
. AddLines ( PROJECT_MARKER 
+  projName 
+  " \n\n " )  356                  # do search in open files first, open files may have been modified and different from disk because it hasn't been saved  357                  openDocs 
=  wx
. GetApp (). GetDocumentManager (). GetDocuments ()  358                  openDocsInProject 
=  filter ( lambda  openDoc
:  openDoc
. GetFilename ()  in  projectFilenames
,  openDocs
)  359                  for  openDoc 
in  openDocsInProject
:  360                      if  isinstance ( openDoc
,  ProjectEditor
. ProjectDocument
):   # don't search project model  363                      openDocView 
=  openDoc
. GetFirstView ()  364                      # some views don't have a in memory text object to search through such as the PM and the DM  365                      # even if they do have a non-text searchable object, how do we display it in the message window?  366                      if not  hasattr ( openDocView
,  "GetValue" ):  368                      text 
=  openDocView
. GetValue ()  371                      needToDisplayFilename 
=  True  376                          count
,  foundStart
,  foundEnd
,  newText 
=  self
. DoFind ( findString
,  None ,  text
,  start
,  end
,  True ,  matchCase
,  wholeWord
,  regExpr
)  378                              if  needToDisplayFilename
:  379                                  view
. AddLines ( FILENAME_MARKER 
+  openDoc
. GetFilename () +  " \n " )  380                                  needToDisplayFilename 
=  False  382                              lineNum 
=  openDocView
. LineFromPosition ( foundStart
)  383                              line 
=  repr ( lineNum
). zfill ( 4 ) +  ":"  +  openDocView
. GetLine ( lineNum
)  386                              start 
=  text
. find ( " \n " ,  foundStart
)  390                      if not  needToDisplayFilename
:  392                  openDocNames 
=  map ( lambda  openDoc
:  openDoc
. GetFilename (),  openDocs
)  394                  # do search in closed files, skipping the open ones we already searched  395                  filenames 
=  filter ( lambda  filename
:  filename 
not in  openDocNames
,  projectFilenames
)  396                  for  filename 
in  filenames
:  398                          docFile 
=  file ( filename
,  'r' )  399                      except  IOError , ( code
,  message
):  400                          print  _ ( "Warning, unable to read file: ' %s '.   %s " ) % ( filename
,  message
)  404                      needToDisplayFilename 
=  True  405                      line 
=  docFile
. readline ()  407                          count
,  foundStart
,  foundEnd
,  newText 
=  self
. DoFind ( findString
,  None ,  line
,  0 ,  0 ,  True ,  matchCase
,  wholeWord
,  regExpr
)  409                              if  needToDisplayFilename
:  410                                  view
. AddLines ( FILENAME_MARKER 
+  filename 
+  " \n " )  411                                  needToDisplayFilename 
=  False  412                              line 
=  repr ( lineNum
). zfill ( 4 ) +  ":"  +  line
 414                          line 
=  docFile
. readline ()  416                      if not  needToDisplayFilename
:  419                  view
. AddLines ( _ ( "Search for ' %s ' completed." ) %  findString
)  426      def  OnJumpToFoundLine ( self
,  event
):  427          messageService 
=  wx
. GetApp (). GetService ( MessageService
. MessageService
)  428          lineText
,  pos 
=  messageService
. GetView (). GetCurrLine ()  429          if  lineText 
==  " \n "  or  lineText
. find ( FILENAME_MARKER
) != - 1  or  lineText
. find ( PROJECT_MARKER
) != - 1 :  431          lineEnd 
=  lineText
. find ( ":" )  435              lineNum 
=  int ( lineText
[ 0 : lineEnd
])  437          text 
=  messageService
. GetView (). GetText ()  438          curPos 
=  messageService
. GetView (). GetCurrentPos ()  440          startPos 
=  text
. rfind ( FILENAME_MARKER
,  0 ,  curPos
)  441          endPos 
=  text
. find ( " \n " ,  startPos
)  442          filename 
=  text
[ startPos 
+  len ( FILENAME_MARKER
): endPos
]  445          openDocs 
=  wx
. GetApp (). GetDocumentManager (). GetDocuments ()  446          for  openDoc 
in  openDocs
:  447              if  openDoc
. GetFilename () ==  filename
:  448                  foundView 
=  openDoc
. GetFirstView ()  452              doc 
=  wx
. GetApp (). GetDocumentManager (). CreateDocument ( filename
,  wx
. lib
. docview
. DOC_SILENT|wx
. lib
. docview
. DOC_OPEN_ONCE
)  454                  foundView 
=  doc
. GetFirstView ()  457              foundView
. GetFrame (). SetFocus ()  459              if  hasattr ( foundView
,  "GotoLine" ):  460                  foundView
. GotoLine ( lineNum
)  461                  startPos 
=  foundView
. PositionFromLine ( lineNum
)  462                  # wxBug:  Need to select in reverse order, (end, start) to put cursor at head of line so positioning is correct  463                  #         Also, if we use the correct positioning order (start, end), somehow, when we open a edit window for the first  464                  #         time, we don't see the selection, it is scrolled off screen  465                  foundView
. SetSelection ( startPos 
-  1  +  len ( lineText
[ lineEnd
:]. rstrip ( " \n " )),  startPos
)  466                  wx
. GetApp (). GetService ( OutlineService
. OutlineService
). LoadOutline ( foundView
,  position
= startPos
)