src/eric7/QScintilla/SearchReplaceWidget.py

branch
eric7
changeset 9221
bf71ee032bb4
parent 9209
b99e7fd55fd3
child 9413
80c06d472826
equal deleted inserted replaced
9220:e9e7eca7efee 9221:bf71ee032bb4
10 import re 10 import re
11 import contextlib 11 import contextlib
12 12
13 from PyQt6.QtCore import pyqtSignal, Qt, pyqtSlot, QEvent 13 from PyQt6.QtCore import pyqtSignal, Qt, pyqtSlot, QEvent
14 from PyQt6.QtWidgets import ( 14 from PyQt6.QtWidgets import (
15 QWidget, QHBoxLayout, QToolButton, QScrollArea, QSizePolicy, QFrame 15 QWidget,
16 QHBoxLayout,
17 QToolButton,
18 QScrollArea,
19 QSizePolicy,
20 QFrame,
16 ) 21 )
17 22
18 from .Editor import Editor 23 from .Editor import Editor
19 24
20 from EricGui.EricAction import EricAction 25 from EricGui.EricAction import EricAction
26 31
27 32
28 class SearchReplaceWidget(QWidget): 33 class SearchReplaceWidget(QWidget):
29 """ 34 """
30 Class implementing the search and replace widget. 35 Class implementing the search and replace widget.
31 36
32 @signal searchListChanged() emitted to indicate a change of the search list 37 @signal searchListChanged() emitted to indicate a change of the search list
33 """ 38 """
39
34 searchListChanged = pyqtSignal() 40 searchListChanged = pyqtSignal()
35 41
36 def __init__(self, replace, vm, parent=None, sliding=False): 42 def __init__(self, replace, vm, parent=None, sliding=False):
37 """ 43 """
38 Constructor 44 Constructor
39 45
40 @param replace flag indicating a replace widget is called 46 @param replace flag indicating a replace widget is called
41 @param vm reference to the viewmanager object 47 @param vm reference to the viewmanager object
42 @param parent parent widget of this widget (QWidget) 48 @param parent parent widget of this widget (QWidget)
43 @param sliding flag indicating the widget is embedded in the 49 @param sliding flag indicating the widget is embedded in the
44 sliding widget (boolean) 50 sliding widget (boolean)
45 """ 51 """
46 super().__init__(parent) 52 super().__init__(parent)
47 53
48 self.__viewmanager = vm 54 self.__viewmanager = vm
49 self.__isMiniEditor = vm is parent 55 self.__isMiniEditor = vm is parent
50 self.__replace = replace 56 self.__replace = replace
51 self.__sliding = sliding 57 self.__sliding = sliding
52 if sliding: 58 if sliding:
53 self.__topWidget = parent 59 self.__topWidget = parent
54 60
55 self.findHistory = vm.getSRHistory('search') 61 self.findHistory = vm.getSRHistory("search")
56 if replace: 62 if replace:
57 from .Ui_ReplaceWidget import Ui_ReplaceWidget 63 from .Ui_ReplaceWidget import Ui_ReplaceWidget
58 self.replaceHistory = vm.getSRHistory('replace') 64
65 self.replaceHistory = vm.getSRHistory("replace")
59 self.ui = Ui_ReplaceWidget() 66 self.ui = Ui_ReplaceWidget()
60 whatsThis = self.tr( 67 whatsThis = self.tr(
61 """<b>Find and Replace</b> 68 """<b>Find and Replace</b>
62 <p>This dialog is used to find some text and replace it with another text. 69 <p>This dialog is used to find some text and replace it with another text.
63 By checking the various checkboxes, the search can be made more specific. 70 By checking the various checkboxes, the search can be made more specific.
65 special characters interpreted are:</p> 72 special characters interpreted are:</p>
66 """ 73 """
67 ) 74 )
68 else: 75 else:
69 from .Ui_SearchWidget import Ui_SearchWidget 76 from .Ui_SearchWidget import Ui_SearchWidget
77
70 self.ui = Ui_SearchWidget() 78 self.ui = Ui_SearchWidget()
71 whatsThis = self.tr( 79 whatsThis = self.tr(
72 """<b>Find</b> 80 """<b>Find</b>
73 <p>This dialog is used to find some text. By checking the various checkboxes, 81 <p>This dialog is used to find some text. By checking the various checkboxes,
74 the search can be made more specific. The search string might be a regular 82 the search can be made more specific. The search string might be a regular
76 """ 84 """
77 ) 85 )
78 self.ui.setupUi(self) 86 self.ui.setupUi(self)
79 if not replace: 87 if not replace:
80 self.ui.wrapCheckBox.setChecked(True) 88 self.ui.wrapCheckBox.setChecked(True)
81 89
82 whatsThis += self.tr( 90 whatsThis += self.tr(
83 """<table border="0"> 91 """<table border="0">
84 <tr><td><code>.</code></td><td>Matches any character</td></tr> 92 <tr><td><code>.</code></td><td>Matches any character</td></tr>
85 <tr><td><code>(</code></td><td>This marks the start of a region for tagging a 93 <tr><td><code>(</code></td><td>This marks the start of a region for tagging a
86 match.</td></tr> 94 match.</td></tr>
125 available, generally similar to regular expression support in JavaScript. See 133 available, generally similar to regular expression support in JavaScript. See
126 the documentation of your C++ runtime for details on what is supported.<p> 134 the documentation of your C++ runtime for details on what is supported.<p>
127 """ 135 """
128 ) 136 )
129 self.setWhatsThis(whatsThis) 137 self.setWhatsThis(whatsThis)
130 138
131 # set icons 139 # set icons
132 self.ui.closeButton.setIcon(UI.PixmapCache.getIcon("close")) 140 self.ui.closeButton.setIcon(UI.PixmapCache.getIcon("close"))
133 self.ui.findPrevButton.setIcon( 141 self.ui.findPrevButton.setIcon(UI.PixmapCache.getIcon("1leftarrow"))
134 UI.PixmapCache.getIcon("1leftarrow")) 142 self.ui.findNextButton.setIcon(UI.PixmapCache.getIcon("1rightarrow"))
135 self.ui.findNextButton.setIcon( 143 self.ui.extendButton.setIcon(UI.PixmapCache.getIcon("2rightarrow"))
136 UI.PixmapCache.getIcon("1rightarrow")) 144
137 self.ui.extendButton.setIcon(
138 UI.PixmapCache.getIcon("2rightarrow"))
139
140 if replace: 145 if replace:
141 self.ui.replaceButton.setIcon( 146 self.ui.replaceButton.setIcon(UI.PixmapCache.getIcon("editReplace"))
142 UI.PixmapCache.getIcon("editReplace"))
143 self.ui.replaceSearchButton.setIcon( 147 self.ui.replaceSearchButton.setIcon(
144 UI.PixmapCache.getIcon("editReplaceSearch")) 148 UI.PixmapCache.getIcon("editReplaceSearch")
145 self.ui.replaceAllButton.setIcon( 149 )
146 UI.PixmapCache.getIcon("editReplaceAll")) 150 self.ui.replaceAllButton.setIcon(UI.PixmapCache.getIcon("editReplaceAll"))
147 151
148 # set line edit completers 152 # set line edit completers
149 self.ui.findtextCombo.setCompleter(None) 153 self.ui.findtextCombo.setCompleter(None)
150 self.ui.findtextCombo.lineEdit().returnPressed.connect( 154 self.ui.findtextCombo.lineEdit().returnPressed.connect(
151 self.__findByReturnPressed) 155 self.__findByReturnPressed
156 )
152 if replace: 157 if replace:
153 self.ui.replacetextCombo.setCompleter(None) 158 self.ui.replacetextCombo.setCompleter(None)
154 self.ui.replacetextCombo.lineEdit().returnPressed.connect( 159 self.ui.replacetextCombo.lineEdit().returnPressed.connect(
155 self.on_replaceButton_clicked) 160 self.on_replaceButton_clicked
156 161 )
162
157 self.ui.findtextCombo.lineEdit().textEdited.connect(self.__quickSearch) 163 self.ui.findtextCombo.lineEdit().textEdited.connect(self.__quickSearch)
158 self.ui.caseCheckBox.toggled.connect( 164 self.ui.caseCheckBox.toggled.connect(self.__updateQuickSearchMarkers)
159 self.__updateQuickSearchMarkers) 165 self.ui.wordCheckBox.toggled.connect(self.__updateQuickSearchMarkers)
160 self.ui.wordCheckBox.toggled.connect( 166 self.ui.regexpCheckBox.toggled.connect(self.__updateQuickSearchMarkers)
161 self.__updateQuickSearchMarkers) 167
162 self.ui.regexpCheckBox.toggled.connect( 168 self.__findtextComboStyleSheet = self.ui.findtextCombo.styleSheet()
163 self.__updateQuickSearchMarkers) 169
164
165 self.__findtextComboStyleSheet = (
166 self.ui.findtextCombo.styleSheet()
167 )
168
169 # define actions 170 # define actions
170 self.findNextAct = EricAction( 171 self.findNextAct = EricAction(
171 self.tr('Find Next'), 172 self.tr("Find Next"),
172 self.tr('Find Next'), 173 self.tr("Find Next"),
173 0, 0, self, 'search_widget_find_next') 174 0,
175 0,
176 self,
177 "search_widget_find_next",
178 )
174 self.findNextAct.triggered.connect(self.on_findNextButton_clicked) 179 self.findNextAct.triggered.connect(self.on_findNextButton_clicked)
175 self.findNextAct.setShortcutContext( 180 self.findNextAct.setShortcutContext(
176 Qt.ShortcutContext.WidgetWithChildrenShortcut) 181 Qt.ShortcutContext.WidgetWithChildrenShortcut
177 182 )
183
178 self.findPrevAct = EricAction( 184 self.findPrevAct = EricAction(
179 self.tr('Find Prev'), 185 self.tr("Find Prev"),
180 self.tr('Find Prev'), 186 self.tr("Find Prev"),
181 0, 0, self, 'search_widget_find_prev') 187 0,
188 0,
189 self,
190 "search_widget_find_prev",
191 )
182 self.findPrevAct.triggered.connect(self.on_findPrevButton_clicked) 192 self.findPrevAct.triggered.connect(self.on_findPrevButton_clicked)
183 self.findPrevAct.setShortcutContext( 193 self.findPrevAct.setShortcutContext(
184 Qt.ShortcutContext.WidgetWithChildrenShortcut) 194 Qt.ShortcutContext.WidgetWithChildrenShortcut
185 195 )
196
186 if replace: 197 if replace:
187 self.replaceAndSearchAct = EricAction( 198 self.replaceAndSearchAct = EricAction(
188 self.tr("Replace and Search"), 199 self.tr("Replace and Search"),
189 self.tr("Replace and Search"), 200 self.tr("Replace and Search"),
190 0, 0, self, "replace_widget_replace_search") 201 0,
202 0,
203 self,
204 "replace_widget_replace_search",
205 )
191 self.replaceAndSearchAct.triggered.connect( 206 self.replaceAndSearchAct.triggered.connect(
192 self.on_replaceSearchButton_clicked) 207 self.on_replaceSearchButton_clicked
208 )
193 self.replaceAndSearchAct.setEnabled(False) 209 self.replaceAndSearchAct.setEnabled(False)
194 self.replaceAndSearchAct.setShortcutContext( 210 self.replaceAndSearchAct.setShortcutContext(
195 Qt.ShortcutContext.WidgetWithChildrenShortcut) 211 Qt.ShortcutContext.WidgetWithChildrenShortcut
196 212 )
213
197 self.replaceSelectionAct = EricAction( 214 self.replaceSelectionAct = EricAction(
198 self.tr("Replace Occurrence"), 215 self.tr("Replace Occurrence"),
199 self.tr("Replace Occurrence"), 216 self.tr("Replace Occurrence"),
200 0, 0, self, "replace_widget_replace_occurrence") 217 0,
201 self.replaceSelectionAct.triggered.connect( 218 0,
202 self.on_replaceButton_clicked) 219 self,
220 "replace_widget_replace_occurrence",
221 )
222 self.replaceSelectionAct.triggered.connect(self.on_replaceButton_clicked)
203 self.replaceSelectionAct.setEnabled(False) 223 self.replaceSelectionAct.setEnabled(False)
204 self.replaceSelectionAct.setShortcutContext( 224 self.replaceSelectionAct.setShortcutContext(
205 Qt.ShortcutContext.WidgetWithChildrenShortcut) 225 Qt.ShortcutContext.WidgetWithChildrenShortcut
206 226 )
227
207 self.replaceAllAct = EricAction( 228 self.replaceAllAct = EricAction(
208 self.tr("Replace All"), 229 self.tr("Replace All"),
209 self.tr("Replace All"), 230 self.tr("Replace All"),
210 0, 0, self, "replace_widget_replace_all") 231 0,
211 self.replaceAllAct.triggered.connect( 232 0,
212 self.on_replaceAllButton_clicked) 233 self,
234 "replace_widget_replace_all",
235 )
236 self.replaceAllAct.triggered.connect(self.on_replaceAllButton_clicked)
213 self.replaceAllAct.setEnabled(False) 237 self.replaceAllAct.setEnabled(False)
214 self.replaceAllAct.setShortcutContext( 238 self.replaceAllAct.setShortcutContext(
215 Qt.ShortcutContext.WidgetWithChildrenShortcut) 239 Qt.ShortcutContext.WidgetWithChildrenShortcut
216 240 )
241
217 self.addAction(self.findNextAct) 242 self.addAction(self.findNextAct)
218 self.addAction(self.findPrevAct) 243 self.addAction(self.findPrevAct)
219 if replace: 244 if replace:
220 self.addAction(self.replaceAndSearchAct) 245 self.addAction(self.replaceAndSearchAct)
221 self.addAction(self.replaceSelectionAct) 246 self.addAction(self.replaceSelectionAct)
222 self.addAction(self.replaceAllAct) 247 self.addAction(self.replaceAllAct)
223 248
224 # disable search and replace buttons and actions 249 # disable search and replace buttons and actions
225 self.__setFindNextEnabled(False) 250 self.__setFindNextEnabled(False)
226 self.__setFindPrevEnabled(False) 251 self.__setFindPrevEnabled(False)
227 if replace: 252 if replace:
228 self.__setReplaceAndSearchEnabled(False) 253 self.__setReplaceAndSearchEnabled(False)
229 self.__setReplaceSelectionEnabled(False) 254 self.__setReplaceSelectionEnabled(False)
230 self.__setReplaceAllEnabled(False) 255 self.__setReplaceAllEnabled(False)
231 256
232 self.adjustSize() 257 self.adjustSize()
233 258
234 self.havefound = False 259 self.havefound = False
235 self.__pos = None 260 self.__pos = None
236 self.__findBackwards = False 261 self.__findBackwards = False
237 self.__selections = [] 262 self.__selections = []
238 self.__finding = False 263 self.__finding = False
239 264
240 def __setShortcuts(self): 265 def __setShortcuts(self):
241 """ 266 """
242 Private method to set the local action's shortcuts to the same key 267 Private method to set the local action's shortcuts to the same key
243 sequences as in the view manager. 268 sequences as in the view manager.
244 """ 269 """
245 if not self.__isMiniEditor: 270 if not self.__isMiniEditor:
246 self.findNextAct.setShortcuts( 271 self.findNextAct.setShortcuts(self.__viewmanager.searchNextAct.shortcuts())
247 self.__viewmanager.searchNextAct.shortcuts()) 272 self.findPrevAct.setShortcuts(self.__viewmanager.searchPrevAct.shortcuts())
248 self.findPrevAct.setShortcuts( 273
249 self.__viewmanager.searchPrevAct.shortcuts())
250
251 if self.__replace: 274 if self.__replace:
252 self.replaceAndSearchAct.setShortcuts( 275 self.replaceAndSearchAct.setShortcuts(
253 self.__viewmanager.replaceAndSearchAct.shortcuts()) 276 self.__viewmanager.replaceAndSearchAct.shortcuts()
277 )
254 self.replaceSelectionAct.setShortcuts( 278 self.replaceSelectionAct.setShortcuts(
255 self.__viewmanager.replaceSelectionAct.shortcuts()) 279 self.__viewmanager.replaceSelectionAct.shortcuts()
280 )
256 self.replaceAllAct.setShortcuts( 281 self.replaceAllAct.setShortcuts(
257 self.__viewmanager.replaceAllAct.shortcuts()) 282 self.__viewmanager.replaceAllAct.shortcuts()
258 283 )
284
259 def __setFindNextEnabled(self, enable): 285 def __setFindNextEnabled(self, enable):
260 """ 286 """
261 Private method to set the enabled state of "Find Next". 287 Private method to set the enabled state of "Find Next".
262 288
263 @param enable flag indicating the enable state to be set 289 @param enable flag indicating the enable state to be set
264 @type bool 290 @type bool
265 """ 291 """
266 self.ui.findNextButton.setEnabled(enable) 292 self.ui.findNextButton.setEnabled(enable)
267 self.findNextAct.setEnabled(enable) 293 self.findNextAct.setEnabled(enable)
268 294
269 def __setFindPrevEnabled(self, enable): 295 def __setFindPrevEnabled(self, enable):
270 """ 296 """
271 Private method to set the enabled state of "Find Prev". 297 Private method to set the enabled state of "Find Prev".
272 298
273 @param enable flag indicating the enable state to be set 299 @param enable flag indicating the enable state to be set
274 @type bool 300 @type bool
275 """ 301 """
276 self.ui.findPrevButton.setEnabled(enable) 302 self.ui.findPrevButton.setEnabled(enable)
277 self.findPrevAct.setEnabled(enable) 303 self.findPrevAct.setEnabled(enable)
278 304
279 def __setReplaceAndSearchEnabled(self, enable): 305 def __setReplaceAndSearchEnabled(self, enable):
280 """ 306 """
281 Private method to set the enabled state of "Replace And Search". 307 Private method to set the enabled state of "Replace And Search".
282 308
283 @param enable flag indicating the enable state to be set 309 @param enable flag indicating the enable state to be set
284 @type bool 310 @type bool
285 """ 311 """
286 self.ui.replaceSearchButton.setEnabled(enable) 312 self.ui.replaceSearchButton.setEnabled(enable)
287 self.replaceAndSearchAct.setEnabled(enable) 313 self.replaceAndSearchAct.setEnabled(enable)
288 314
289 def __setReplaceSelectionEnabled(self, enable): 315 def __setReplaceSelectionEnabled(self, enable):
290 """ 316 """
291 Private method to set the enabled state of "Replace Occurrence". 317 Private method to set the enabled state of "Replace Occurrence".
292 318
293 @param enable flag indicating the enable state to be set 319 @param enable flag indicating the enable state to be set
294 @type bool 320 @type bool
295 """ 321 """
296 self.ui.replaceButton.setEnabled(enable) 322 self.ui.replaceButton.setEnabled(enable)
297 self.replaceSelectionAct.setEnabled(enable) 323 self.replaceSelectionAct.setEnabled(enable)
298 324
299 def __setReplaceAllEnabled(self, enable): 325 def __setReplaceAllEnabled(self, enable):
300 """ 326 """
301 Private method to set the enabled state of "Replace All". 327 Private method to set the enabled state of "Replace All".
302 328
303 @param enable flag indicating the enable state to be set 329 @param enable flag indicating the enable state to be set
304 @type bool 330 @type bool
305 """ 331 """
306 self.ui.replaceAllButton.setEnabled(enable) 332 self.ui.replaceAllButton.setEnabled(enable)
307 self.replaceAllAct.setEnabled(enable) 333 self.replaceAllAct.setEnabled(enable)
308 334
309 def changeEvent(self, evt): 335 def changeEvent(self, evt):
310 """ 336 """
311 Protected method handling state changes. 337 Protected method handling state changes.
312 338
313 @param evt event containing the state change (QEvent) 339 @param evt event containing the state change (QEvent)
314 """ 340 """
315 if evt.type() == QEvent.Type.FontChange: 341 if evt.type() == QEvent.Type.FontChange:
316 self.adjustSize() 342 self.adjustSize()
317 343
318 def __selectionBoundary(self, selections=None): 344 def __selectionBoundary(self, selections=None):
319 """ 345 """
320 Private method to calculate the current selection boundary. 346 Private method to calculate the current selection boundary.
321 347
322 @param selections optional parameter giving the selections to 348 @param selections optional parameter giving the selections to
323 calculate the boundary for (list of tuples of four integer) 349 calculate the boundary for (list of tuples of four integer)
324 @return tuple of start line and index and end line and index 350 @return tuple of start line and index and end line and index
325 (tuple of four integer) 351 (tuple of four integer)
326 """ 352 """
327 if selections is None: 353 if selections is None:
328 selections = self.__selections 354 selections = self.__selections
329 if selections: 355 if selections:
330 lineNumbers = ( 356 lineNumbers = [sel[0] for sel in selections] + [
331 [sel[0] for sel in selections] + 357 sel[2] for sel in selections
332 [sel[2] for sel in selections] 358 ]
333 ) 359 indexNumbers = [sel[1] for sel in selections] + [
334 indexNumbers = ( 360 sel[3] for sel in selections
335 [sel[1] for sel in selections] + 361 ]
336 [sel[3] for sel in selections]
337 )
338 startLine, startIndex, endLine, endIndex = ( 362 startLine, startIndex, endLine, endIndex = (
339 min(lineNumbers), min(indexNumbers), 363 min(lineNumbers),
340 max(lineNumbers), max(indexNumbers)) 364 min(indexNumbers),
365 max(lineNumbers),
366 max(indexNumbers),
367 )
341 else: 368 else:
342 startLine, startIndex, endLine, endIndex = -1, -1, -1, -1 369 startLine, startIndex, endLine, endIndex = -1, -1, -1, -1
343 370
344 return startLine, startIndex, endLine, endIndex 371 return startLine, startIndex, endLine, endIndex
345 372
346 @pyqtSlot(str) 373 @pyqtSlot(str)
347 def on_findtextCombo_editTextChanged(self, txt): 374 def on_findtextCombo_editTextChanged(self, txt):
348 """ 375 """
349 Private slot to enable/disable the find buttons. 376 Private slot to enable/disable the find buttons.
350 377
351 @param txt text of the find text combo 378 @param txt text of the find text combo
352 @type str 379 @type str
353 """ 380 """
354 enable = bool(txt) 381 enable = bool(txt)
355 382
356 self.__setFindNextEnabled(enable) 383 self.__setFindNextEnabled(enable)
357 self.__setFindPrevEnabled(enable) 384 self.__setFindPrevEnabled(enable)
358 self.ui.extendButton.setEnabled(enable) 385 self.ui.extendButton.setEnabled(enable)
359 if self.__replace: 386 if self.__replace:
360 self.__setReplaceSelectionEnabled(False) 387 self.__setReplaceSelectionEnabled(False)
361 self.__setReplaceAndSearchEnabled(False) 388 self.__setReplaceAndSearchEnabled(False)
362 self.__setReplaceAllEnabled(enable) 389 self.__setReplaceAllEnabled(enable)
363 390
364 @pyqtSlot(str) 391 @pyqtSlot(str)
365 def __quickSearch(self, txt): 392 def __quickSearch(self, txt):
366 """ 393 """
367 Private slot to search for the entered text while typing. 394 Private slot to search for the entered text while typing.
368 395
369 @param txt text of the search edit 396 @param txt text of the search edit
370 @type str 397 @type str
371 """ 398 """
372 aw = self.__viewmanager.activeWindow() 399 aw = self.__viewmanager.activeWindow()
373 aw.hideFindIndicator() 400 aw.hideFindIndicator()
374 if Preferences.getEditor("QuickSearchMarkersEnabled"): 401 if Preferences.getEditor("QuickSearchMarkersEnabled"):
375 self.__quickSearchMarkOccurrences(txt) 402 self.__quickSearchMarkOccurrences(txt)
376 403
377 lineFrom, indexFrom, lineTo, indexTo = aw.getSelection() 404 lineFrom, indexFrom, lineTo, indexTo = aw.getSelection()
378 posixMode = (Preferences.getEditor("SearchRegexpMode") == 0 and 405 posixMode = (
379 self.ui.regexpCheckBox.isChecked()) 406 Preferences.getEditor("SearchRegexpMode") == 0
380 cxx11Mode = (Preferences.getEditor("SearchRegexpMode") == 1 and 407 and self.ui.regexpCheckBox.isChecked()
381 self.ui.regexpCheckBox.isChecked()) 408 )
409 cxx11Mode = (
410 Preferences.getEditor("SearchRegexpMode") == 1
411 and self.ui.regexpCheckBox.isChecked()
412 )
382 ok = aw.findFirst( 413 ok = aw.findFirst(
383 txt, 414 txt,
384 self.ui.regexpCheckBox.isChecked(), 415 self.ui.regexpCheckBox.isChecked(),
385 self.ui.caseCheckBox.isChecked(), 416 self.ui.caseCheckBox.isChecked(),
386 self.ui.wordCheckBox.isChecked(), 417 self.ui.wordCheckBox.isChecked(),
387 self.ui.wrapCheckBox.isChecked(), 418 self.ui.wrapCheckBox.isChecked(),
388 not self.__findBackwards, 419 not self.__findBackwards,
389 lineFrom, indexFrom, 420 lineFrom,
421 indexFrom,
390 posix=posixMode, 422 posix=posixMode,
391 cxx11=cxx11Mode 423 cxx11=cxx11Mode,
392 ) 424 )
393 if ok: 425 if ok:
394 sline, sindex, eline, eindex = aw.getSelection() 426 sline, sindex, eline, eindex = aw.getSelection()
395 aw.showFindIndicator(sline, sindex, eline, eindex) 427 aw.showFindIndicator(sline, sindex, eline, eindex)
396 428
397 if not txt: 429 if not txt:
398 ok = True # reset the color in case of an empty text 430 ok = True # reset the color in case of an empty text
399 431
400 self.__setSearchEditColors(ok) 432 self.__setSearchEditColors(ok)
401 433
402 def __quickSearchMarkOccurrences(self, txt): 434 def __quickSearchMarkOccurrences(self, txt):
403 """ 435 """
404 Private method to mark all occurrences of the search text. 436 Private method to mark all occurrences of the search text.
405 437
406 @param txt text to search for (string) 438 @param txt text to search for (string)
407 """ 439 """
408 aw = self.__viewmanager.activeWindow() 440 aw = self.__viewmanager.activeWindow()
409 441
410 lineFrom = 0 442 lineFrom = 0
411 indexFrom = 0 443 indexFrom = 0
412 lineTo = -1 444 lineTo = -1
413 indexTo = -1 445 indexTo = -1
414 446
415 aw.clearSearchIndicators() 447 aw.clearSearchIndicators()
416 posixMode = (Preferences.getEditor("SearchRegexpMode") == 0 and 448 posixMode = (
417 self.ui.regexpCheckBox.isChecked()) 449 Preferences.getEditor("SearchRegexpMode") == 0
418 cxx11Mode = (Preferences.getEditor("SearchRegexpMode") == 1 and 450 and self.ui.regexpCheckBox.isChecked()
419 self.ui.regexpCheckBox.isChecked()) 451 )
452 cxx11Mode = (
453 Preferences.getEditor("SearchRegexpMode") == 1
454 and self.ui.regexpCheckBox.isChecked()
455 )
420 ok = aw.findFirstTarget( 456 ok = aw.findFirstTarget(
421 txt, 457 txt,
422 self.ui.regexpCheckBox.isChecked(), 458 self.ui.regexpCheckBox.isChecked(),
423 self.ui.caseCheckBox.isChecked(), 459 self.ui.caseCheckBox.isChecked(),
424 self.ui.wordCheckBox.isChecked(), 460 self.ui.wordCheckBox.isChecked(),
425 lineFrom, indexFrom, lineTo, indexTo, 461 lineFrom,
462 indexFrom,
463 lineTo,
464 indexTo,
426 posix=posixMode, 465 posix=posixMode,
427 cxx11=cxx11Mode 466 cxx11=cxx11Mode,
428 ) 467 )
429 while ok: 468 while ok:
430 tgtPos, tgtLen = aw.getFoundTarget() 469 tgtPos, tgtLen = aw.getFoundTarget()
431 aw.setSearchIndicator(tgtPos, tgtLen) 470 aw.setSearchIndicator(tgtPos, tgtLen)
432 ok = aw.findNextTarget() 471 ok = aw.findNextTarget()
433 472
434 def __setSearchEditColors(self, ok): 473 def __setSearchEditColors(self, ok):
435 """ 474 """
436 Private method to set the search edit colors. 475 Private method to set the search edit colors.
437 476
438 @param ok flag indicating a match 477 @param ok flag indicating a match
439 @type bool 478 @type bool
440 """ 479 """
441 if not ok: 480 if not ok:
442 self.ui.findtextCombo.setStyleSheet( 481 self.ui.findtextCombo.setStyleSheet(
443 "color: #000000; background-color: #ff6666;" 482 "color: #000000; background-color: #ff6666;"
444 ) 483 )
445 else: 484 else:
446 self.ui.findtextCombo.setStyleSheet( 485 self.ui.findtextCombo.setStyleSheet(self.__findtextComboStyleSheet)
447 self.__findtextComboStyleSheet) 486
448
449 @pyqtSlot() 487 @pyqtSlot()
450 def on_extendButton_clicked(self): 488 def on_extendButton_clicked(self):
451 """ 489 """
452 Private slot to handle the quicksearch extend action. 490 Private slot to handle the quicksearch extend action.
453 """ 491 """
454 aw = self.__viewmanager.activeWindow() 492 aw = self.__viewmanager.activeWindow()
455 if aw is None: 493 if aw is None:
456 return 494 return
457 495
458 txt = self.ui.findtextCombo.currentText() 496 txt = self.ui.findtextCombo.currentText()
459 if not txt: 497 if not txt:
460 return 498 return
461 499
462 line, index = aw.getCursorPosition() 500 line, index = aw.getCursorPosition()
463 text = aw.text(line) 501 text = aw.text(line)
464 502
465 rx = re.compile(r'[^\w_]') 503 rx = re.compile(r"[^\w_]")
466 match = rx.search(text, index) 504 match = rx.search(text, index)
467 if match: 505 if match:
468 end = match.start() 506 end = match.start()
469 if end > index: 507 if end > index:
470 ext = text[index:end] 508 ext = text[index:end]
471 txt += ext 509 txt += ext
472 self.ui.findtextCombo.setEditText(txt) 510 self.ui.findtextCombo.setEditText(txt)
473 self.ui.findtextCombo.lineEdit().selectAll() 511 self.ui.findtextCombo.lineEdit().selectAll()
474 self.__quickSearch(txt) 512 self.__quickSearch(txt)
475 513
476 @pyqtSlot(bool) 514 @pyqtSlot(bool)
477 def __updateQuickSearchMarkers(self, on): 515 def __updateQuickSearchMarkers(self, on):
478 """ 516 """
479 Private slot to handle the selection of the various check boxes. 517 Private slot to handle the selection of the various check boxes.
480 518
481 @param on status of the check box (ignored) 519 @param on status of the check box (ignored)
482 @type bool 520 @type bool
483 """ 521 """
484 txt = self.ui.findtextCombo.currentText() 522 txt = self.ui.findtextCombo.currentText()
485 self.__quickSearch(txt) 523 self.__quickSearch(txt)
486 524
487 @pyqtSlot() 525 @pyqtSlot()
488 def on_findNextButton_clicked(self): 526 def on_findNextButton_clicked(self):
489 """ 527 """
490 Private slot to find the next occurrence of text. 528 Private slot to find the next occurrence of text.
491 """ 529 """
492 self.findNext() 530 self.findNext()
493 531
494 def findNext(self): 532 def findNext(self):
495 """ 533 """
496 Public slot to find the next occurrence of text. 534 Public slot to find the next occurrence of text.
497 """ 535 """
498 if not self.havefound or not self.ui.findtextCombo.currentText(): 536 if not self.havefound or not self.ui.findtextCombo.currentText():
499 if self.__replace: 537 if self.__replace:
500 self.__viewmanager.showReplaceWidget() 538 self.__viewmanager.showReplaceWidget()
501 else: 539 else:
502 self.__viewmanager.showSearchWidget() 540 self.__viewmanager.showSearchWidget()
503 return 541 return
504 542
505 self.__findBackwards = False 543 self.__findBackwards = False
506 txt = self.ui.findtextCombo.currentText() 544 txt = self.ui.findtextCombo.currentText()
507 545
508 # This moves any previous occurrence of this statement to the head 546 # This moves any previous occurrence of this statement to the head
509 # of the list and updates the combobox 547 # of the list and updates the combobox
510 if txt in self.findHistory: 548 if txt in self.findHistory:
511 self.findHistory.remove(txt) 549 self.findHistory.remove(txt)
512 self.findHistory.insert(0, txt) 550 self.findHistory.insert(0, txt)
513 self.ui.findtextCombo.clear() 551 self.ui.findtextCombo.clear()
514 self.ui.findtextCombo.addItems(self.findHistory) 552 self.ui.findtextCombo.addItems(self.findHistory)
515 self.searchListChanged.emit() 553 self.searchListChanged.emit()
516 554
517 ok = self.__findNextPrev(txt, False) 555 ok = self.__findNextPrev(txt, False)
518 self.__setSearchEditColors(ok) 556 self.__setSearchEditColors(ok)
519 if ok: 557 if ok:
520 if self.__replace: 558 if self.__replace:
521 self.__setReplaceSelectionEnabled(True) 559 self.__setReplaceSelectionEnabled(True)
522 self.__setReplaceAndSearchEnabled(True) 560 self.__setReplaceAndSearchEnabled(True)
523 else: 561 else:
524 EricMessageBox.information( 562 EricMessageBox.information(
525 self, self.windowTitle(), 563 self, self.windowTitle(), self.tr("'{0}' was not found.").format(txt)
526 self.tr("'{0}' was not found.").format(txt)) 564 )
527 565
528 @pyqtSlot() 566 @pyqtSlot()
529 def on_findPrevButton_clicked(self): 567 def on_findPrevButton_clicked(self):
530 """ 568 """
531 Private slot to find the previous occurrence of text. 569 Private slot to find the previous occurrence of text.
532 """ 570 """
533 self.findPrev() 571 self.findPrev()
534 572
535 def findPrev(self): 573 def findPrev(self):
536 """ 574 """
537 Public slot to find the next previous of text. 575 Public slot to find the next previous of text.
538 """ 576 """
539 if not self.havefound or not self.ui.findtextCombo.currentText(): 577 if not self.havefound or not self.ui.findtextCombo.currentText():
540 self.show(self.__viewmanager.textForFind()) 578 self.show(self.__viewmanager.textForFind())
541 return 579 return
542 580
543 self.__findBackwards = True 581 self.__findBackwards = True
544 txt = self.ui.findtextCombo.currentText() 582 txt = self.ui.findtextCombo.currentText()
545 583
546 # This moves any previous occurrence of this statement to the head 584 # This moves any previous occurrence of this statement to the head
547 # of the list and updates the combobox 585 # of the list and updates the combobox
548 if txt in self.findHistory: 586 if txt in self.findHistory:
549 self.findHistory.remove(txt) 587 self.findHistory.remove(txt)
550 self.findHistory.insert(0, txt) 588 self.findHistory.insert(0, txt)
551 self.ui.findtextCombo.clear() 589 self.ui.findtextCombo.clear()
552 self.ui.findtextCombo.addItems(self.findHistory) 590 self.ui.findtextCombo.addItems(self.findHistory)
553 self.searchListChanged.emit() 591 self.searchListChanged.emit()
554 592
555 ok = self.__findNextPrev(txt, True) 593 ok = self.__findNextPrev(txt, True)
556 self.__setSearchEditColors(ok) 594 self.__setSearchEditColors(ok)
557 if ok: 595 if ok:
558 if self.__replace: 596 if self.__replace:
559 self.__setReplaceSelectionEnabled(True) 597 self.__setReplaceSelectionEnabled(True)
560 self.__setReplaceAndSearchEnabled(True) 598 self.__setReplaceAndSearchEnabled(True)
561 else: 599 else:
562 EricMessageBox.information( 600 EricMessageBox.information(
563 self, self.windowTitle(), 601 self, self.windowTitle(), self.tr("'{0}' was not found.").format(txt)
564 self.tr("'{0}' was not found.").format(txt)) 602 )
565 603
566 def __findByReturnPressed(self): 604 def __findByReturnPressed(self):
567 """ 605 """
568 Private slot to handle the returnPressed signal of the findtext 606 Private slot to handle the returnPressed signal of the findtext
569 combobox. 607 combobox.
570 """ 608 """
571 if self.__findBackwards: 609 if self.__findBackwards:
572 self.findPrev() 610 self.findPrev()
573 else: 611 else:
574 self.findNext() 612 self.findNext()
575 613
576 def __markOccurrences(self, txt): 614 def __markOccurrences(self, txt):
577 """ 615 """
578 Private method to mark all occurrences of the search text. 616 Private method to mark all occurrences of the search text.
579 617
580 @param txt text to search for (string) 618 @param txt text to search for (string)
581 """ 619 """
582 aw = self.__viewmanager.activeWindow() 620 aw = self.__viewmanager.activeWindow()
583 lineFrom = 0 621 lineFrom = 0
584 indexFrom = 0 622 indexFrom = 0
585 lineTo = -1 623 lineTo = -1
586 indexTo = -1 624 indexTo = -1
587 if self.ui.selectionCheckBox.isChecked(): 625 if self.ui.selectionCheckBox.isChecked():
588 lineFrom, indexFrom, lineTo, indexTo = self.__selectionBoundary() 626 lineFrom, indexFrom, lineTo, indexTo = self.__selectionBoundary()
589 posixMode = (Preferences.getEditor("SearchRegexpMode") == 0 and 627 posixMode = (
590 self.ui.regexpCheckBox.isChecked()) 628 Preferences.getEditor("SearchRegexpMode") == 0
591 cxx11Mode = (Preferences.getEditor("SearchRegexpMode") == 1 and 629 and self.ui.regexpCheckBox.isChecked()
592 self.ui.regexpCheckBox.isChecked()) 630 )
593 631 cxx11Mode = (
632 Preferences.getEditor("SearchRegexpMode") == 1
633 and self.ui.regexpCheckBox.isChecked()
634 )
635
594 aw.clearSearchIndicators() 636 aw.clearSearchIndicators()
595 ok = aw.findFirstTarget( 637 ok = aw.findFirstTarget(
596 txt, 638 txt,
597 self.ui.regexpCheckBox.isChecked(), 639 self.ui.regexpCheckBox.isChecked(),
598 self.ui.caseCheckBox.isChecked(), 640 self.ui.caseCheckBox.isChecked(),
599 self.ui.wordCheckBox.isChecked(), 641 self.ui.wordCheckBox.isChecked(),
600 lineFrom, indexFrom, lineTo, indexTo, 642 lineFrom,
601 posix=posixMode, cxx11=cxx11Mode) 643 indexFrom,
644 lineTo,
645 indexTo,
646 posix=posixMode,
647 cxx11=cxx11Mode,
648 )
602 while ok: 649 while ok:
603 tgtPos, tgtLen = aw.getFoundTarget() 650 tgtPos, tgtLen = aw.getFoundTarget()
604 if tgtLen == 0: 651 if tgtLen == 0:
605 break 652 break
606 if len(self.__selections) > 1: 653 if len(self.__selections) > 1:
607 lineFrom, indexFrom = aw.lineIndexFromPosition(tgtPos) 654 lineFrom, indexFrom = aw.lineIndexFromPosition(tgtPos)
608 lineTo, indexTo = aw.lineIndexFromPosition(tgtPos + tgtLen) 655 lineTo, indexTo = aw.lineIndexFromPosition(tgtPos + tgtLen)
609 for sel in self.__selections: 656 for sel in self.__selections:
610 if ( 657 if lineFrom == sel[0] and indexFrom >= sel[1] and indexTo <= sel[3]:
611 lineFrom == sel[0] and
612 indexFrom >= sel[1] and
613 indexTo <= sel[3]
614 ):
615 indicate = True 658 indicate = True
616 break 659 break
617 else: 660 else:
618 indicate = False 661 indicate = False
619 else: 662 else:
622 aw.setSearchIndicator(tgtPos, tgtLen) 665 aw.setSearchIndicator(tgtPos, tgtLen)
623 ok = aw.findNextTarget() 666 ok = aw.findNextTarget()
624 with contextlib.suppress(AttributeError): 667 with contextlib.suppress(AttributeError):
625 aw.updateMarkerMap() 668 aw.updateMarkerMap()
626 # ignore it for MiniEditor 669 # ignore it for MiniEditor
627 670
628 def __findNextPrev(self, txt, backwards): 671 def __findNextPrev(self, txt, backwards):
629 """ 672 """
630 Private method to find the next occurrence of the search text. 673 Private method to find the next occurrence of the search text.
631 674
632 @param txt text to search for (string) 675 @param txt text to search for (string)
633 @param backwards flag indicating a backwards search (boolean) 676 @param backwards flag indicating a backwards search (boolean)
634 @return flag indicating success (boolean) 677 @return flag indicating success (boolean)
635 """ 678 """
636 self.__finding = True 679 self.__finding = True
637 680
638 if Preferences.getEditor("SearchMarkersEnabled"): 681 if Preferences.getEditor("SearchMarkersEnabled"):
639 self.__markOccurrences(txt) 682 self.__markOccurrences(txt)
640 683
641 aw = self.__viewmanager.activeWindow() 684 aw = self.__viewmanager.activeWindow()
642 aw.hideFindIndicator() 685 aw.hideFindIndicator()
643 cline, cindex = aw.getCursorPosition() 686 cline, cindex = aw.getCursorPosition()
644 687
645 ok = True 688 ok = True
646 lineFrom, indexFrom, lineTo, indexTo = aw.getSelection() 689 lineFrom, indexFrom, lineTo, indexTo = aw.getSelection()
647 boundary = self.__selectionBoundary() 690 boundary = self.__selectionBoundary()
648 if backwards: 691 if backwards:
649 if ( 692 if (
650 self.ui.selectionCheckBox.isChecked() and 693 self.ui.selectionCheckBox.isChecked()
651 (lineFrom, indexFrom, lineTo, indexTo) == boundary 694 and (lineFrom, indexFrom, lineTo, indexTo) == boundary
652 ): 695 ):
653 # initial call 696 # initial call
654 line, index = boundary[2:] 697 line, index = boundary[2:]
655 else: 698 else:
656 if (lineFrom, indexFrom) == (-1, -1): 699 if (lineFrom, indexFrom) == (-1, -1):
659 index = cindex 702 index = cindex
660 else: 703 else:
661 line = lineFrom 704 line = lineFrom
662 index = indexFrom 705 index = indexFrom
663 if ( 706 if (
664 self.ui.selectionCheckBox.isChecked() and 707 self.ui.selectionCheckBox.isChecked()
665 line == boundary[0] and 708 and line == boundary[0]
666 index >= 0 and 709 and index >= 0
667 index < boundary[1] 710 and index < boundary[1]
668 ): 711 ):
669 ok = False 712 ok = False
670 713
671 if ok and index < 0: 714 if ok and index < 0:
672 line -= 1 715 line -= 1
673 if self.ui.selectionCheckBox.isChecked(): 716 if self.ui.selectionCheckBox.isChecked():
674 if line < boundary[0]: 717 if line < boundary[0]:
675 if self.ui.wrapCheckBox.isChecked(): 718 if self.ui.wrapCheckBox.isChecked():
687 ok = False 730 ok = False
688 else: 731 else:
689 index = aw.lineLength(line) 732 index = aw.lineLength(line)
690 else: 733 else:
691 if ( 734 if (
692 self.ui.selectionCheckBox.isChecked() and 735 self.ui.selectionCheckBox.isChecked()
693 (lineFrom, indexFrom, lineTo, indexTo) == boundary 736 and (lineFrom, indexFrom, lineTo, indexTo) == boundary
694 ): 737 ):
695 # initial call 738 # initial call
696 line, index = boundary[:2] 739 line, index = boundary[:2]
697 else: 740 else:
698 line = lineTo 741 line = lineTo
699 index = indexTo 742 index = indexTo
700 743
701 if ok: 744 if ok:
702 posixMode = (Preferences.getEditor("SearchRegexpMode") == 0 and 745 posixMode = (
703 self.ui.regexpCheckBox.isChecked()) 746 Preferences.getEditor("SearchRegexpMode") == 0
704 cxx11Mode = (Preferences.getEditor("SearchRegexpMode") == 1 and 747 and self.ui.regexpCheckBox.isChecked()
705 self.ui.regexpCheckBox.isChecked()) 748 )
749 cxx11Mode = (
750 Preferences.getEditor("SearchRegexpMode") == 1
751 and self.ui.regexpCheckBox.isChecked()
752 )
706 ok = aw.findFirst( 753 ok = aw.findFirst(
707 txt, 754 txt,
708 self.ui.regexpCheckBox.isChecked(), 755 self.ui.regexpCheckBox.isChecked(),
709 self.ui.caseCheckBox.isChecked(), 756 self.ui.caseCheckBox.isChecked(),
710 self.ui.wordCheckBox.isChecked(), 757 self.ui.wordCheckBox.isChecked(),
711 self.ui.wrapCheckBox.isChecked(), 758 self.ui.wrapCheckBox.isChecked(),
712 not backwards, 759 not backwards,
713 line, index, 760 line,
761 index,
714 posix=posixMode, 762 posix=posixMode,
715 cxx11=cxx11Mode) 763 cxx11=cxx11Mode,
716 764 )
765
717 if ok and self.ui.selectionCheckBox.isChecked(): 766 if ok and self.ui.selectionCheckBox.isChecked():
718 lineFrom, indexFrom, lineTo, indexTo = aw.getSelection() 767 lineFrom, indexFrom, lineTo, indexTo = aw.getSelection()
719 if len(self.__selections) > 1: 768 if len(self.__selections) > 1:
720 for sel in self.__selections: 769 for sel in self.__selections:
721 if ( 770 if lineFrom == sel[0] and indexFrom >= sel[1] and indexTo <= sel[3]:
722 lineFrom == sel[0] and
723 indexFrom >= sel[1] and
724 indexTo <= sel[3]
725 ):
726 ok = True 771 ok = True
727 break 772 break
728 else: 773 else:
729 ok = False 774 ok = False
730 elif ( 775 elif (
731 (lineFrom == boundary[0] and indexFrom >= boundary[1]) or 776 (lineFrom == boundary[0] and indexFrom >= boundary[1])
732 (lineFrom > boundary[0] and lineFrom < boundary[2]) or 777 or (lineFrom > boundary[0] and lineFrom < boundary[2])
733 (lineFrom == boundary[2] and indexFrom <= boundary[3]) 778 or (lineFrom == boundary[2] and indexFrom <= boundary[3])
734 ): 779 ):
735 ok = True 780 ok = True
736 else: 781 else:
737 ok = False 782 ok = False
738 if not ok and len(self.__selections) > 1: 783 if not ok and len(self.__selections) > 1:
739 # try again 784 # try again
740 while ( 785 while not ok and (
741 not ok and 786 (backwards and lineFrom >= boundary[0])
742 ((backwards and lineFrom >= boundary[0]) or 787 or (not backwards and lineFrom <= boundary[2])
743 (not backwards and lineFrom <= boundary[2]))
744 ): 788 ):
745 for ind in range(len(self.__selections)): 789 for ind in range(len(self.__selections)):
746 if lineFrom == self.__selections[ind][0]: 790 if lineFrom == self.__selections[ind][0]:
747 after = indexTo > self.__selections[ind][3] 791 after = indexTo > self.__selections[ind][3]
748 if backwards: 792 if backwards:
749 if after: 793 if after:
750 line, index = self.__selections[ind][2:] 794 line, index = self.__selections[ind][2:]
751 else: 795 else:
752 if ind > 0: 796 if ind > 0:
753 line, index = ( 797 line, index = self.__selections[ind - 1][2:]
754 self.__selections[ind - 1][2:]
755 )
756 else: 798 else:
757 if after: 799 if after:
758 if ind < len(self.__selections) - 1: 800 if ind < len(self.__selections) - 1:
759 line, index = ( 801 line, index = self.__selections[ind + 1][:2]
760 self.__selections[ind + 1][:2]
761 )
762 else: 802 else:
763 line, index = self.__selections[ind][:2] 803 line, index = self.__selections[ind][:2]
764 break 804 break
765 else: 805 else:
766 break 806 break
769 self.ui.regexpCheckBox.isChecked(), 809 self.ui.regexpCheckBox.isChecked(),
770 self.ui.caseCheckBox.isChecked(), 810 self.ui.caseCheckBox.isChecked(),
771 self.ui.wordCheckBox.isChecked(), 811 self.ui.wordCheckBox.isChecked(),
772 self.ui.wrapCheckBox.isChecked(), 812 self.ui.wrapCheckBox.isChecked(),
773 not backwards, 813 not backwards,
774 line, index, 814 line,
815 index,
775 posix=posixMode, 816 posix=posixMode,
776 cxx11=cxx11Mode) 817 cxx11=cxx11Mode,
818 )
777 if ok: 819 if ok:
778 lineFrom, indexFrom, lineTo, indexTo = ( 820 lineFrom, indexFrom, lineTo, indexTo = aw.getSelection()
779 aw.getSelection()
780 )
781 if ( 821 if (
782 lineFrom < boundary[0] or 822 lineFrom < boundary[0]
783 lineFrom > boundary[2] or 823 or lineFrom > boundary[2]
784 indexFrom < boundary[1] or 824 or indexFrom < boundary[1]
785 indexFrom > boundary[3] or 825 or indexFrom > boundary[3]
786 indexTo < boundary[1] or 826 or indexTo < boundary[1]
787 indexTo > boundary[3] 827 or indexTo > boundary[3]
788 ): 828 ):
789 ok = False 829 ok = False
790 break 830 break
791 if not ok: 831 if not ok:
792 if self.ui.wrapCheckBox.isChecked(): 832 if self.ui.wrapCheckBox.isChecked():
800 self.ui.regexpCheckBox.isChecked(), 840 self.ui.regexpCheckBox.isChecked(),
801 self.ui.caseCheckBox.isChecked(), 841 self.ui.caseCheckBox.isChecked(),
802 self.ui.wordCheckBox.isChecked(), 842 self.ui.wordCheckBox.isChecked(),
803 self.ui.wrapCheckBox.isChecked(), 843 self.ui.wrapCheckBox.isChecked(),
804 not backwards, 844 not backwards,
805 line, index, 845 line,
846 index,
806 posix=posixMode, 847 posix=posixMode,
807 cxx11=cxx11Mode) 848 cxx11=cxx11Mode,
849 )
808 if ok: 850 if ok:
809 lineFrom, indexFrom, lineTo, indexTo = ( 851 lineFrom, indexFrom, lineTo, indexTo = aw.getSelection()
810 aw.getSelection()
811 )
812 if len(self.__selections) > 1: 852 if len(self.__selections) > 1:
813 for sel in self.__selections: 853 for sel in self.__selections:
814 if ( 854 if (
815 lineFrom == sel[0] and 855 lineFrom == sel[0]
816 indexFrom >= sel[1] and 856 and indexFrom >= sel[1]
817 indexTo <= sel[3] 857 and indexTo <= sel[3]
818 ): 858 ):
819 ok = True 859 ok = True
820 break 860 break
821 else: 861 else:
822 ok = False 862 ok = False
823 elif ( 863 elif (
824 (lineFrom == boundary[0] and 864 (lineFrom == boundary[0] and indexFrom >= boundary[1])
825 indexFrom >= boundary[1]) or 865 or (lineFrom > boundary[0] and lineFrom < boundary[2])
826 (lineFrom > boundary[0] and 866 or (lineFrom == boundary[2] and indexFrom <= boundary[3])
827 lineFrom < boundary[2]) or
828 (lineFrom == boundary[2] and
829 indexFrom <= boundary[3])
830 ): 867 ):
831 ok = True 868 ok = True
832 else: 869 else:
833 ok = False 870 ok = False
834 else: 871 else:
835 ok = False 872 ok = False
836 873
837 if not ok: 874 if not ok:
838 aw.selectAll(False) 875 aw.selectAll(False)
839 aw.setCursorPosition(cline, cindex) 876 aw.setCursorPosition(cline, cindex)
840 aw.ensureCursorVisible() 877 aw.ensureCursorVisible()
841 878
842 if ok: 879 if ok:
843 sline, sindex, eline, eindex = aw.getSelection() 880 sline, sindex, eline, eindex = aw.getSelection()
844 aw.showFindIndicator(sline, sindex, eline, eindex) 881 aw.showFindIndicator(sline, sindex, eline, eindex)
845 882
846 self.__finding = False 883 self.__finding = False
847 884
848 return ok 885 return ok
849 886
850 def __showFind(self, text=''): 887 def __showFind(self, text=""):
851 """ 888 """
852 Private method to display this widget in find mode. 889 Private method to display this widget in find mode.
853 890
854 @param text text to be shown in the findtext edit (string) 891 @param text text to be shown in the findtext edit (string)
855 """ 892 """
856 self.__replace = False 893 self.__replace = False
857 894
858 self.__setSearchEditColors(True) 895 self.__setSearchEditColors(True)
859 self.ui.findtextCombo.clear() 896 self.ui.findtextCombo.clear()
860 self.ui.findtextCombo.addItems(self.findHistory) 897 self.ui.findtextCombo.addItems(self.findHistory)
861 self.ui.findtextCombo.setEditText(text) 898 self.ui.findtextCombo.setEditText(text)
862 self.ui.findtextCombo.lineEdit().selectAll() 899 self.ui.findtextCombo.lineEdit().selectAll()
863 self.ui.findtextCombo.setFocus() 900 self.ui.findtextCombo.setFocus()
864 self.on_findtextCombo_editTextChanged(text) 901 self.on_findtextCombo_editTextChanged(text)
865 902
866 self.ui.caseCheckBox.setChecked(False) 903 self.ui.caseCheckBox.setChecked(False)
867 self.ui.wordCheckBox.setChecked(False) 904 self.ui.wordCheckBox.setChecked(False)
868 self.ui.wrapCheckBox.setChecked(True) 905 self.ui.wrapCheckBox.setChecked(True)
869 self.ui.regexpCheckBox.setChecked(False) 906 self.ui.regexpCheckBox.setChecked(False)
870 907
871 aw = self.__viewmanager.activeWindow() 908 aw = self.__viewmanager.activeWindow()
872 self.updateSelectionCheckBox(aw) 909 self.updateSelectionCheckBox(aw)
873 910
874 self.havefound = True 911 self.havefound = True
875 self.__findBackwards = False 912 self.__findBackwards = False
876 913
877 self.__setShortcuts() 914 self.__setShortcuts()
878 915
879 def selectionChanged(self, editor): 916 def selectionChanged(self, editor):
880 """ 917 """
881 Public slot tracking changes of selected text. 918 Public slot tracking changes of selected text.
882 919
883 @param editor reference to the editor 920 @param editor reference to the editor
884 @type Editor 921 @type Editor
885 """ 922 """
886 self.updateSelectionCheckBox(editor) 923 self.updateSelectionCheckBox(editor)
887 924
888 @pyqtSlot(Editor) 925 @pyqtSlot(Editor)
889 def updateSelectionCheckBox(self, editor): 926 def updateSelectionCheckBox(self, editor):
890 """ 927 """
891 Public slot to update the selection check box. 928 Public slot to update the selection check box.
892 929
893 @param editor reference to the editor 930 @param editor reference to the editor
894 @type Editor 931 @type Editor
895 """ 932 """
896 if not self.__finding and isinstance(editor, Editor): 933 if not self.__finding and isinstance(editor, Editor):
897 if editor.hasSelectedText(): 934 if editor.hasSelectedText():
898 selections = editor.getSelections() 935 selections = editor.getSelections()
899 line1, index1, line2, index2 = ( 936 line1, index1, line2, index2 = self.__selectionBoundary(selections)
900 self.__selectionBoundary(selections)
901 )
902 if line1 != line2: 937 if line1 != line2:
903 self.ui.selectionCheckBox.setEnabled(True) 938 self.ui.selectionCheckBox.setEnabled(True)
904 self.ui.selectionCheckBox.setChecked(True) 939 self.ui.selectionCheckBox.setChecked(True)
905 self.__selections = selections 940 self.__selections = selections
906 return 941 return
907 942
908 self.ui.selectionCheckBox.setEnabled(False) 943 self.ui.selectionCheckBox.setEnabled(False)
909 self.ui.selectionCheckBox.setChecked(False) 944 self.ui.selectionCheckBox.setChecked(False)
910 self.__selections = [] 945 self.__selections = []
911 946
912 def replace(self): 947 def replace(self):
913 """ 948 """
914 Public method to replace the current selection. 949 Public method to replace the current selection.
915 """ 950 """
916 if self.ui.replaceButton.isEnabled(): 951 if self.ui.replaceButton.isEnabled():
917 self.__doReplace(False) 952 self.__doReplace(False)
918 953
919 def replaceSearch(self): 954 def replaceSearch(self):
920 """ 955 """
921 Public method to replace the current selection and search again. 956 Public method to replace the current selection and search again.
922 """ 957 """
923 if self.ui.replaceSearchButton.isEnabled(): 958 if self.ui.replaceSearchButton.isEnabled():
924 self.__doReplace(True) 959 self.__doReplace(True)
925 960
926 @pyqtSlot() 961 @pyqtSlot()
927 def on_replaceButton_clicked(self): 962 def on_replaceButton_clicked(self):
928 """ 963 """
929 Private slot to replace one occurrence of text. 964 Private slot to replace one occurrence of text.
930 """ 965 """
931 self.__doReplace(False) 966 self.__doReplace(False)
932 967
933 @pyqtSlot() 968 @pyqtSlot()
934 def on_replaceSearchButton_clicked(self): 969 def on_replaceSearchButton_clicked(self):
935 """ 970 """
936 Private slot to replace one occurrence of text and search for the next 971 Private slot to replace one occurrence of text and search for the next
937 one. 972 one.
938 """ 973 """
939 self.__doReplace(True) 974 self.__doReplace(True)
940 975
941 def __doReplace(self, searchNext): 976 def __doReplace(self, searchNext):
942 """ 977 """
943 Private method to replace one occurrence of text. 978 Private method to replace one occurrence of text.
944 979
945 @param searchNext flag indicating to search for the next occurrence 980 @param searchNext flag indicating to search for the next occurrence
946 (boolean). 981 (boolean).
947 """ 982 """
948 self.__finding = True 983 self.__finding = True
949 984
950 # Check enabled status due to dual purpose usage of this method 985 # Check enabled status due to dual purpose usage of this method
951 if ( 986 if (
952 not self.ui.replaceButton.isEnabled() and 987 not self.ui.replaceButton.isEnabled()
953 not self.ui.replaceSearchButton.isEnabled() 988 and not self.ui.replaceSearchButton.isEnabled()
954 ): 989 ):
955 return 990 return
956 991
957 ftxt = self.ui.findtextCombo.currentText() 992 ftxt = self.ui.findtextCombo.currentText()
958 rtxt = self.ui.replacetextCombo.currentText() 993 rtxt = self.ui.replacetextCombo.currentText()
959 994
960 # This moves any previous occurrence of this statement to the head 995 # This moves any previous occurrence of this statement to the head
961 # of the list and updates the combobox 996 # of the list and updates the combobox
962 if rtxt in self.replaceHistory: 997 if rtxt in self.replaceHistory:
963 self.replaceHistory.remove(rtxt) 998 self.replaceHistory.remove(rtxt)
964 self.replaceHistory.insert(0, rtxt) 999 self.replaceHistory.insert(0, rtxt)
965 self.ui.replacetextCombo.clear() 1000 self.ui.replacetextCombo.clear()
966 self.ui.replacetextCombo.addItems(self.replaceHistory) 1001 self.ui.replacetextCombo.addItems(self.replaceHistory)
967 1002
968 aw = self.__viewmanager.activeWindow() 1003 aw = self.__viewmanager.activeWindow()
969 aw.hideFindIndicator() 1004 aw.hideFindIndicator()
970 aw.replace(rtxt) 1005 aw.replace(rtxt)
971 1006
972 if searchNext: 1007 if searchNext:
973 ok = self.__findNextPrev(ftxt, self.__findBackwards) 1008 ok = self.__findNextPrev(ftxt, self.__findBackwards)
974 self.__setSearchEditColors(ok) 1009 self.__setSearchEditColors(ok)
975 1010
976 if not ok: 1011 if not ok:
977 self.__setReplaceSelectionEnabled(False) 1012 self.__setReplaceSelectionEnabled(False)
978 self.__setReplaceAndSearchEnabled(False) 1013 self.__setReplaceAndSearchEnabled(False)
979 EricMessageBox.information( 1014 EricMessageBox.information(
980 self, self.windowTitle(), 1015 self,
981 self.tr("'{0}' was not found.").format(ftxt)) 1016 self.windowTitle(),
1017 self.tr("'{0}' was not found.").format(ftxt),
1018 )
982 else: 1019 else:
983 self.__setReplaceSelectionEnabled(False) 1020 self.__setReplaceSelectionEnabled(False)
984 self.__setReplaceAndSearchEnabled(False) 1021 self.__setReplaceAndSearchEnabled(False)
985 self.__setSearchEditColors(True) 1022 self.__setSearchEditColors(True)
986 1023
987 self.__finding = False 1024 self.__finding = False
988 1025
989 def replaceAll(self): 1026 def replaceAll(self):
990 """ 1027 """
991 Public method to replace all occurrences. 1028 Public method to replace all occurrences.
992 """ 1029 """
993 if self.ui.replaceAllButton.isEnabled(): 1030 if self.ui.replaceAllButton.isEnabled():
994 self.on_replaceAllButton_clicked() 1031 self.on_replaceAllButton_clicked()
995 1032
996 @pyqtSlot() 1033 @pyqtSlot()
997 def on_replaceAllButton_clicked(self): 1034 def on_replaceAllButton_clicked(self):
998 """ 1035 """
999 Private slot to replace all occurrences of text. 1036 Private slot to replace all occurrences of text.
1000 """ 1037 """
1001 self.__finding = True 1038 self.__finding = True
1002 1039
1003 replacements = 0 1040 replacements = 0
1004 ftxt = self.ui.findtextCombo.currentText() 1041 ftxt = self.ui.findtextCombo.currentText()
1005 rtxt = self.ui.replacetextCombo.currentText() 1042 rtxt = self.ui.replacetextCombo.currentText()
1006 1043
1007 # This moves any previous occurrence of this statement to the head 1044 # This moves any previous occurrence of this statement to the head
1008 # of the list and updates the combobox 1045 # of the list and updates the combobox
1009 if ftxt in self.findHistory: 1046 if ftxt in self.findHistory:
1010 self.findHistory.remove(ftxt) 1047 self.findHistory.remove(ftxt)
1011 self.findHistory.insert(0, ftxt) 1048 self.findHistory.insert(0, ftxt)
1012 self.ui.findtextCombo.clear() 1049 self.ui.findtextCombo.clear()
1013 self.ui.findtextCombo.addItems(self.findHistory) 1050 self.ui.findtextCombo.addItems(self.findHistory)
1014 1051
1015 if rtxt in self.replaceHistory: 1052 if rtxt in self.replaceHistory:
1016 self.replaceHistory.remove(rtxt) 1053 self.replaceHistory.remove(rtxt)
1017 self.replaceHistory.insert(0, rtxt) 1054 self.replaceHistory.insert(0, rtxt)
1018 self.ui.replacetextCombo.clear() 1055 self.ui.replacetextCombo.clear()
1019 self.ui.replacetextCombo.addItems(self.replaceHistory) 1056 self.ui.replacetextCombo.addItems(self.replaceHistory)
1020 1057
1021 aw = self.__viewmanager.activeWindow() 1058 aw = self.__viewmanager.activeWindow()
1022 aw.hideFindIndicator() 1059 aw.hideFindIndicator()
1023 cline, cindex = aw.getCursorPosition() 1060 cline, cindex = aw.getCursorPosition()
1024 boundary = self.__selectionBoundary() 1061 boundary = self.__selectionBoundary()
1025 if self.ui.selectionCheckBox.isChecked(): 1062 if self.ui.selectionCheckBox.isChecked():
1026 line, index = boundary[:2] 1063 line, index = boundary[:2]
1027 else: 1064 else:
1028 line = 0 1065 line = 0
1029 index = 0 1066 index = 0
1030 posixMode = (Preferences.getEditor("SearchRegexpMode") == 0 and 1067 posixMode = (
1031 self.ui.regexpCheckBox.isChecked()) 1068 Preferences.getEditor("SearchRegexpMode") == 0
1032 cxx11Mode = (Preferences.getEditor("SearchRegexpMode") == 1 and 1069 and self.ui.regexpCheckBox.isChecked()
1033 self.ui.regexpCheckBox.isChecked()) 1070 )
1071 cxx11Mode = (
1072 Preferences.getEditor("SearchRegexpMode") == 1
1073 and self.ui.regexpCheckBox.isChecked()
1074 )
1034 ok = aw.findFirst( 1075 ok = aw.findFirst(
1035 ftxt, 1076 ftxt,
1036 self.ui.regexpCheckBox.isChecked(), 1077 self.ui.regexpCheckBox.isChecked(),
1037 self.ui.caseCheckBox.isChecked(), 1078 self.ui.caseCheckBox.isChecked(),
1038 self.ui.wordCheckBox.isChecked(), 1079 self.ui.wordCheckBox.isChecked(),
1039 False, True, line, index, 1080 False,
1081 True,
1082 line,
1083 index,
1040 posix=posixMode, 1084 posix=posixMode,
1041 cxx11=cxx11Mode) 1085 cxx11=cxx11Mode,
1042 1086 )
1087
1043 if ok and self.ui.selectionCheckBox.isChecked(): 1088 if ok and self.ui.selectionCheckBox.isChecked():
1044 lineFrom, indexFrom, lineTo, indexTo = aw.getSelection() 1089 lineFrom, indexFrom, lineTo, indexTo = aw.getSelection()
1045 if len(self.__selections) > 1: 1090 if len(self.__selections) > 1:
1046 for sel in self.__selections: 1091 for sel in self.__selections:
1047 if ( 1092 if lineFrom == sel[0] and indexFrom >= sel[1] and indexTo <= sel[3]:
1048 lineFrom == sel[0] and
1049 indexFrom >= sel[1] and
1050 indexTo <= sel[3]
1051 ):
1052 ok = True 1093 ok = True
1053 break 1094 break
1054 else: 1095 else:
1055 ok = False 1096 ok = False
1056 elif ( 1097 elif (
1057 (lineFrom == boundary[0] and indexFrom >= boundary[1]) or 1098 (lineFrom == boundary[0] and indexFrom >= boundary[1])
1058 (lineFrom > boundary[0] and lineFrom < boundary[2]) or 1099 or (lineFrom > boundary[0] and lineFrom < boundary[2])
1059 (lineFrom == boundary[2] and indexFrom <= boundary[3]) 1100 or (lineFrom == boundary[2] and indexFrom <= boundary[3])
1060 ): 1101 ):
1061 ok = True 1102 ok = True
1062 else: 1103 else:
1063 ok = False 1104 ok = False
1064 if not ok and len(self.__selections) > 1: 1105 if not ok and len(self.__selections) > 1:
1067 for ind in range(len(self.__selections)): 1108 for ind in range(len(self.__selections)):
1068 if lineFrom == self.__selections[ind][0]: 1109 if lineFrom == self.__selections[ind][0]:
1069 after = indexTo > self.__selections[ind][3] 1110 after = indexTo > self.__selections[ind][3]
1070 if after: 1111 if after:
1071 if ind < len(self.__selections) - 1: 1112 if ind < len(self.__selections) - 1:
1072 line, index = ( 1113 line, index = self.__selections[ind + 1][:2]
1073 self.__selections[ind + 1][:2]
1074 )
1075 else: 1114 else:
1076 line, index = self.__selections[ind][:2] 1115 line, index = self.__selections[ind][:2]
1077 break 1116 break
1078 else: 1117 else:
1079 break 1118 break
1080 ok = aw.findFirst( 1119 ok = aw.findFirst(
1081 ftxt, 1120 ftxt,
1082 self.ui.regexpCheckBox.isChecked(), 1121 self.ui.regexpCheckBox.isChecked(),
1083 self.ui.caseCheckBox.isChecked(), 1122 self.ui.caseCheckBox.isChecked(),
1084 self.ui.wordCheckBox.isChecked(), 1123 self.ui.wordCheckBox.isChecked(),
1085 False, True, line, index, 1124 False,
1125 True,
1126 line,
1127 index,
1086 posix=posixMode, 1128 posix=posixMode,
1087 cxx11=cxx11Mode) 1129 cxx11=cxx11Mode,
1130 )
1088 if ok: 1131 if ok:
1089 lineFrom, indexFrom, lineTo, indexTo = ( 1132 lineFrom, indexFrom, lineTo, indexTo = aw.getSelection()
1090 aw.getSelection()
1091 )
1092 if ( 1133 if (
1093 lineFrom < boundary[0] or 1134 lineFrom < boundary[0]
1094 lineFrom > boundary[2] or 1135 or lineFrom > boundary[2]
1095 indexFrom < boundary[1] or 1136 or indexFrom < boundary[1]
1096 indexFrom > boundary[3] or 1137 or indexFrom > boundary[3]
1097 indexTo < boundary[1] or 1138 or indexTo < boundary[1]
1098 indexTo > boundary[3] 1139 or indexTo > boundary[3]
1099 ): 1140 ):
1100 ok = False 1141 ok = False
1101 break 1142 break
1102 1143
1103 if not ok: 1144 if not ok:
1104 aw.selectAll(False) 1145 aw.selectAll(False)
1105 aw.setCursorPosition(cline, cindex) 1146 aw.setCursorPosition(cline, cindex)
1106 aw.ensureCursorVisible() 1147 aw.ensureCursorVisible()
1107 1148
1108 found = ok 1149 found = ok
1109 1150
1110 aw.beginUndoAction() 1151 aw.beginUndoAction()
1111 wordWrap = self.ui.wrapCheckBox.isChecked() 1152 wordWrap = self.ui.wrapCheckBox.isChecked()
1112 self.ui.wrapCheckBox.setChecked(False) 1153 self.ui.wrapCheckBox.setChecked(False)
1113 while ok: 1154 while ok:
1114 aw.replace(rtxt) 1155 aw.replace(rtxt)
1118 aw.endUndoAction() 1159 aw.endUndoAction()
1119 if wordWrap: 1160 if wordWrap:
1120 self.ui.wrapCheckBox.setChecked(True) 1161 self.ui.wrapCheckBox.setChecked(True)
1121 self.__setReplaceSelectionEnabled(False) 1162 self.__setReplaceSelectionEnabled(False)
1122 self.__setReplaceAndSearchEnabled(False) 1163 self.__setReplaceAndSearchEnabled(False)
1123 1164
1124 if found: 1165 if found:
1125 EricMessageBox.information( 1166 EricMessageBox.information(
1126 self, self.windowTitle(), 1167 self,
1127 self.tr("Replaced {0} occurrences.") 1168 self.windowTitle(),
1128 .format(replacements)) 1169 self.tr("Replaced {0} occurrences.").format(replacements),
1170 )
1129 else: 1171 else:
1130 EricMessageBox.information( 1172 EricMessageBox.information(
1131 self, self.windowTitle(), 1173 self,
1132 self.tr("Nothing replaced because '{0}' was not found.") 1174 self.windowTitle(),
1133 .format(ftxt)) 1175 self.tr("Nothing replaced because '{0}' was not found.").format(ftxt),
1134 1176 )
1177
1135 aw.setCursorPosition(cline, cindex) 1178 aw.setCursorPosition(cline, cindex)
1136 aw.ensureCursorVisible() 1179 aw.ensureCursorVisible()
1137 1180
1138 self.__finding = False 1181 self.__finding = False
1139 1182
1140 def __showReplace(self, text=''): 1183 def __showReplace(self, text=""):
1141 """ 1184 """
1142 Private slot to display this widget in replace mode. 1185 Private slot to display this widget in replace mode.
1143 1186
1144 @param text text to be shown in the findtext edit 1187 @param text text to be shown in the findtext edit
1145 """ 1188 """
1146 self.__replace = True 1189 self.__replace = True
1147 1190
1148 self.__setSearchEditColors(True) 1191 self.__setSearchEditColors(True)
1149 self.ui.findtextCombo.clear() 1192 self.ui.findtextCombo.clear()
1150 self.ui.findtextCombo.addItems(self.findHistory) 1193 self.ui.findtextCombo.addItems(self.findHistory)
1151 self.ui.findtextCombo.setEditText(text) 1194 self.ui.findtextCombo.setEditText(text)
1152 self.ui.findtextCombo.lineEdit().selectAll() 1195 self.ui.findtextCombo.lineEdit().selectAll()
1153 self.ui.findtextCombo.setFocus() 1196 self.ui.findtextCombo.setFocus()
1154 self.on_findtextCombo_editTextChanged(text) 1197 self.on_findtextCombo_editTextChanged(text)
1155 1198
1156 self.ui.replacetextCombo.clear() 1199 self.ui.replacetextCombo.clear()
1157 self.ui.replacetextCombo.addItems(self.replaceHistory) 1200 self.ui.replacetextCombo.addItems(self.replaceHistory)
1158 self.ui.replacetextCombo.setEditText('') 1201 self.ui.replacetextCombo.setEditText("")
1159 1202
1160 self.ui.caseCheckBox.setChecked(False) 1203 self.ui.caseCheckBox.setChecked(False)
1161 self.ui.wordCheckBox.setChecked(False) 1204 self.ui.wordCheckBox.setChecked(False)
1162 self.ui.regexpCheckBox.setChecked(False) 1205 self.ui.regexpCheckBox.setChecked(False)
1163 1206
1164 self.havefound = True 1207 self.havefound = True
1165 1208
1166 aw = self.__viewmanager.activeWindow() 1209 aw = self.__viewmanager.activeWindow()
1167 self.updateSelectionCheckBox(aw) 1210 self.updateSelectionCheckBox(aw)
1168 if aw.hasSelectedText(): 1211 if aw.hasSelectedText():
1169 line1, index1, line2, index2 = aw.getSelection() 1212 line1, index1, line2, index2 = aw.getSelection()
1170 if line1 == line2: 1213 if line1 == line2:
1171 aw.setSelection(line1, index1, line1, index1) 1214 aw.setSelection(line1, index1, line1, index1)
1172 self.findNext() 1215 self.findNext()
1173 1216
1174 self.__setShortcuts() 1217 self.__setShortcuts()
1175 1218
1176 def show(self, text=''): 1219 def show(self, text=""):
1177 """ 1220 """
1178 Public slot to show the widget. 1221 Public slot to show the widget.
1179 1222
1180 @param text text to be shown in the findtext edit (string) 1223 @param text text to be shown in the findtext edit (string)
1181 """ 1224 """
1182 if self.__replace: 1225 if self.__replace:
1183 self.__showReplace(text) 1226 self.__showReplace(text)
1184 else: 1227 else:
1192 Private slot to close the widget. 1235 Private slot to close the widget.
1193 """ 1236 """
1194 aw = self.__viewmanager.activeWindow() 1237 aw = self.__viewmanager.activeWindow()
1195 if aw: 1238 if aw:
1196 aw.hideFindIndicator() 1239 aw.hideFindIndicator()
1197 1240
1198 if self.__sliding: 1241 if self.__sliding:
1199 self.__topWidget.close() 1242 self.__topWidget.close()
1200 else: 1243 else:
1201 self.close() 1244 self.close()
1202 1245
1203 def keyPressEvent(self, event): 1246 def keyPressEvent(self, event):
1204 """ 1247 """
1205 Protected slot to handle key press events. 1248 Protected slot to handle key press events.
1206 1249
1207 @param event reference to the key press event (QKeyEvent) 1250 @param event reference to the key press event (QKeyEvent)
1208 """ 1251 """
1209 if event.key() == Qt.Key.Key_Escape: 1252 if event.key() == Qt.Key.Key_Escape:
1210 aw = self.__viewmanager.activeWindow() 1253 aw = self.__viewmanager.activeWindow()
1211 if aw: 1254 if aw:
1219 1262
1220 1263
1221 class SearchReplaceSlidingWidget(QWidget): 1264 class SearchReplaceSlidingWidget(QWidget):
1222 """ 1265 """
1223 Class implementing the search and replace widget with sliding behavior. 1266 Class implementing the search and replace widget with sliding behavior.
1224 1267
1225 @signal searchListChanged() emitted to indicate a change of the search list 1268 @signal searchListChanged() emitted to indicate a change of the search list
1226 """ 1269 """
1270
1227 searchListChanged = pyqtSignal() 1271 searchListChanged = pyqtSignal()
1228 1272
1229 def __init__(self, replace, vm, parent=None): 1273 def __init__(self, replace, vm, parent=None):
1230 """ 1274 """
1231 Constructor 1275 Constructor
1232 1276
1233 @param replace flag indicating a replace widget is called 1277 @param replace flag indicating a replace widget is called
1234 @param vm reference to the viewmanager object 1278 @param vm reference to the viewmanager object
1235 @param parent parent widget of this widget (QWidget) 1279 @param parent parent widget of this widget (QWidget)
1236 """ 1280 """
1237 super().__init__(parent) 1281 super().__init__(parent)
1238 1282
1239 self.__searchReplaceWidget = SearchReplaceWidget( 1283 self.__searchReplaceWidget = SearchReplaceWidget(replace, vm, self, True)
1240 replace, vm, self, True) 1284
1241
1242 self.__layout = QHBoxLayout(self) 1285 self.__layout = QHBoxLayout(self)
1243 self.setLayout(self.__layout) 1286 self.setLayout(self.__layout)
1244 self.__layout.setContentsMargins(0, 0, 0, 0) 1287 self.__layout.setContentsMargins(0, 0, 0, 0)
1245 self.__layout.setAlignment(Qt.AlignmentFlag.AlignTop) 1288 self.__layout.setAlignment(Qt.AlignmentFlag.AlignTop)
1246 1289
1247 self.__leftButton = QToolButton(self) 1290 self.__leftButton = QToolButton(self)
1248 self.__leftButton.setArrowType(Qt.ArrowType.LeftArrow) 1291 self.__leftButton.setArrowType(Qt.ArrowType.LeftArrow)
1249 self.__leftButton.setSizePolicy( 1292 self.__leftButton.setSizePolicy(
1250 QSizePolicy.Policy.Minimum, QSizePolicy.Policy.MinimumExpanding) 1293 QSizePolicy.Policy.Minimum, QSizePolicy.Policy.MinimumExpanding
1294 )
1251 self.__leftButton.setAutoRepeat(True) 1295 self.__leftButton.setAutoRepeat(True)
1252 1296
1253 self.__scroller = QScrollArea(self) 1297 self.__scroller = QScrollArea(self)
1254 self.__scroller.setWidget(self.__searchReplaceWidget) 1298 self.__scroller.setWidget(self.__searchReplaceWidget)
1255 self.__scroller.setSizePolicy( 1299 self.__scroller.setSizePolicy(
1256 QSizePolicy.Policy.Expanding, QSizePolicy.Policy.Minimum) 1300 QSizePolicy.Policy.Expanding, QSizePolicy.Policy.Minimum
1301 )
1257 self.__scroller.setFrameShape(QFrame.Shape.NoFrame) 1302 self.__scroller.setFrameShape(QFrame.Shape.NoFrame)
1258 self.__scroller.setVerticalScrollBarPolicy( 1303 self.__scroller.setVerticalScrollBarPolicy(
1259 Qt.ScrollBarPolicy.ScrollBarAlwaysOff) 1304 Qt.ScrollBarPolicy.ScrollBarAlwaysOff
1305 )
1260 self.__scroller.setHorizontalScrollBarPolicy( 1306 self.__scroller.setHorizontalScrollBarPolicy(
1261 Qt.ScrollBarPolicy.ScrollBarAlwaysOff) 1307 Qt.ScrollBarPolicy.ScrollBarAlwaysOff
1308 )
1262 self.__scroller.setWidgetResizable(False) 1309 self.__scroller.setWidgetResizable(False)
1263 1310
1264 self.__rightButton = QToolButton(self) 1311 self.__rightButton = QToolButton(self)
1265 self.__rightButton.setArrowType(Qt.ArrowType.RightArrow) 1312 self.__rightButton.setArrowType(Qt.ArrowType.RightArrow)
1266 self.__rightButton.setSizePolicy( 1313 self.__rightButton.setSizePolicy(
1267 QSizePolicy.Policy.Minimum, QSizePolicy.Policy.MinimumExpanding) 1314 QSizePolicy.Policy.Minimum, QSizePolicy.Policy.MinimumExpanding
1315 )
1268 self.__rightButton.setAutoRepeat(True) 1316 self.__rightButton.setAutoRepeat(True)
1269 1317
1270 self.__layout.addWidget(self.__leftButton) 1318 self.__layout.addWidget(self.__leftButton)
1271 self.__layout.addWidget(self.__scroller) 1319 self.__layout.addWidget(self.__scroller)
1272 self.__layout.addWidget(self.__rightButton) 1320 self.__layout.addWidget(self.__rightButton)
1273 1321
1274 self.setMaximumHeight(self.__searchReplaceWidget.sizeHint().height()) 1322 self.setMaximumHeight(self.__searchReplaceWidget.sizeHint().height())
1275 self.adjustSize() 1323 self.adjustSize()
1276 1324
1277 self.__searchReplaceWidget.searchListChanged.connect( 1325 self.__searchReplaceWidget.searchListChanged.connect(self.searchListChanged)
1278 self.searchListChanged)
1279 self.__leftButton.clicked.connect(self.__slideLeft) 1326 self.__leftButton.clicked.connect(self.__slideLeft)
1280 self.__rightButton.clicked.connect(self.__slideRight) 1327 self.__rightButton.clicked.connect(self.__slideRight)
1281 1328
1282 def changeEvent(self, evt): 1329 def changeEvent(self, evt):
1283 """ 1330 """
1284 Protected method handling state changes. 1331 Protected method handling state changes.
1285 1332
1286 @param evt event containing the state change (QEvent) 1333 @param evt event containing the state change (QEvent)
1287 """ 1334 """
1288 if evt.type() == QEvent.Type.FontChange: 1335 if evt.type() == QEvent.Type.FontChange:
1289 self.setMaximumHeight( 1336 self.setMaximumHeight(self.__searchReplaceWidget.sizeHint().height())
1290 self.__searchReplaceWidget.sizeHint().height())
1291 self.adjustSize() 1337 self.adjustSize()
1292 1338
1293 def findNext(self): 1339 def findNext(self):
1294 """ 1340 """
1295 Public slot to find the next occurrence of text. 1341 Public slot to find the next occurrence of text.
1296 """ 1342 """
1297 self.__searchReplaceWidget.findNext() 1343 self.__searchReplaceWidget.findNext()
1298 1344
1299 def findPrev(self): 1345 def findPrev(self):
1300 """ 1346 """
1301 Public slot to find the next previous of text. 1347 Public slot to find the next previous of text.
1302 """ 1348 """
1303 self.__searchReplaceWidget.findPrev() 1349 self.__searchReplaceWidget.findPrev()
1304 1350
1305 def replace(self): 1351 def replace(self):
1306 """ 1352 """
1307 Public method to replace the current selection. 1353 Public method to replace the current selection.
1308 """ 1354 """
1309 self.__searchReplaceWidget.replace() 1355 self.__searchReplaceWidget.replace()
1310 1356
1311 def replaceSearch(self): 1357 def replaceSearch(self):
1312 """ 1358 """
1313 Public method to replace the current selection and search again. 1359 Public method to replace the current selection and search again.
1314 """ 1360 """
1315 self.__searchReplaceWidget.replaceSearch() 1361 self.__searchReplaceWidget.replaceSearch()
1316 1362
1317 def replaceAll(self): 1363 def replaceAll(self):
1318 """ 1364 """
1319 Public method to replace all occurrences. 1365 Public method to replace all occurrences.
1320 """ 1366 """
1321 self.__searchReplaceWidget.replaceAll() 1367 self.__searchReplaceWidget.replaceAll()
1322 1368
1323 def selectionChanged(self, editor): 1369 def selectionChanged(self, editor):
1324 """ 1370 """
1325 Public slot tracking changes of selected text. 1371 Public slot tracking changes of selected text.
1326 1372
1327 @param editor reference to the editor 1373 @param editor reference to the editor
1328 @type Editor 1374 @type Editor
1329 """ 1375 """
1330 self.__searchReplaceWidget.updateSelectionCheckBox(editor) 1376 self.__searchReplaceWidget.updateSelectionCheckBox(editor)
1331 1377
1332 @pyqtSlot(Editor) 1378 @pyqtSlot(Editor)
1333 def updateSelectionCheckBox(self, editor): 1379 def updateSelectionCheckBox(self, editor):
1334 """ 1380 """
1335 Public slot to update the selection check box. 1381 Public slot to update the selection check box.
1336 1382
1337 @param editor reference to the editor (Editor) 1383 @param editor reference to the editor (Editor)
1338 """ 1384 """
1339 self.__searchReplaceWidget.updateSelectionCheckBox(editor) 1385 self.__searchReplaceWidget.updateSelectionCheckBox(editor)
1340 1386
1341 def show(self, text=''): 1387 def show(self, text=""):
1342 """ 1388 """
1343 Public slot to show the widget. 1389 Public slot to show the widget.
1344 1390
1345 @param text text to be shown in the findtext edit (string) 1391 @param text text to be shown in the findtext edit (string)
1346 """ 1392 """
1347 self.__searchReplaceWidget.show(text) 1393 self.__searchReplaceWidget.show(text)
1348 super().show() 1394 super().show()
1349 self.__enableScrollerButtons() 1395 self.__enableScrollerButtons()
1350 1396
1351 def __slideLeft(self): 1397 def __slideLeft(self):
1352 """ 1398 """
1353 Private slot to move the widget to the left, i.e. show contents to the 1399 Private slot to move the widget to the left, i.e. show contents to the
1354 right. 1400 right.
1355 """ 1401 """
1356 self.__slide(True) 1402 self.__slide(True)
1357 1403
1358 def __slideRight(self): 1404 def __slideRight(self):
1359 """ 1405 """
1360 Private slot to move the widget to the right, i.e. show contents to 1406 Private slot to move the widget to the right, i.e. show contents to
1361 the left. 1407 the left.
1362 """ 1408 """
1363 self.__slide(False) 1409 self.__slide(False)
1364 1410
1365 def __slide(self, toLeft): 1411 def __slide(self, toLeft):
1366 """ 1412 """
1367 Private method to move the sliding widget. 1413 Private method to move the sliding widget.
1368 1414
1369 @param toLeft flag indicating to move to the left (boolean) 1415 @param toLeft flag indicating to move to the left (boolean)
1370 """ 1416 """
1371 scrollBar = self.__scroller.horizontalScrollBar() 1417 scrollBar = self.__scroller.horizontalScrollBar()
1372 stepSize = scrollBar.singleStep() 1418 stepSize = scrollBar.singleStep()
1373 if toLeft: 1419 if toLeft:
1377 newValue = 0 1423 newValue = 0
1378 elif newValue > scrollBar.maximum(): 1424 elif newValue > scrollBar.maximum():
1379 newValue = scrollBar.maximum() 1425 newValue = scrollBar.maximum()
1380 scrollBar.setValue(newValue) 1426 scrollBar.setValue(newValue)
1381 self.__enableScrollerButtons() 1427 self.__enableScrollerButtons()
1382 1428
1383 def __enableScrollerButtons(self): 1429 def __enableScrollerButtons(self):
1384 """ 1430 """
1385 Private method to set the enabled state of the scroll buttons. 1431 Private method to set the enabled state of the scroll buttons.
1386 """ 1432 """
1387 scrollBar = self.__scroller.horizontalScrollBar() 1433 scrollBar = self.__scroller.horizontalScrollBar()
1388 self.__leftButton.setEnabled(scrollBar.value() > 0) 1434 self.__leftButton.setEnabled(scrollBar.value() > 0)
1389 self.__rightButton.setEnabled(scrollBar.value() < scrollBar.maximum()) 1435 self.__rightButton.setEnabled(scrollBar.value() < scrollBar.maximum())
1390 1436
1391 def resizeEvent(self, evt): 1437 def resizeEvent(self, evt):
1392 """ 1438 """
1393 Protected method to handle resize events. 1439 Protected method to handle resize events.
1394 1440
1395 @param evt reference to the resize event (QResizeEvent) 1441 @param evt reference to the resize event (QResizeEvent)
1396 """ 1442 """
1397 self.__enableScrollerButtons() 1443 self.__enableScrollerButtons()
1398 1444
1399 super().resizeEvent(evt) 1445 super().resizeEvent(evt)

eric ide

mercurial