##// END OF EJS Templates
Numerous fixes to ConsoleWidget editing region maintenence code. It now impossible (or at least very difficult :) to break the input region.
epatters -
Show More
@@ -221,8 +221,13 b' class ConsoleWidget(QtGui.QWidget):'
221 221 def _set_input_buffer(self, string):
222 222 """ Replaces the text in the input buffer with 'string'.
223 223 """
224 # For now, it is an error to modify the input buffer during execution.
225 if self._executing:
226 raise RuntimeError("Cannot change input buffer during execution.")
227
224 228 # Remove old text.
225 229 cursor = self._get_end_cursor()
230 cursor.beginEditBlock()
226 231 cursor.setPosition(self._prompt_pos, QtGui.QTextCursor.KeepAnchor)
227 232 cursor.removeSelectedText()
228 233
@@ -236,6 +241,7 b' class ConsoleWidget(QtGui.QWidget):'
236 241 else:
237 242 self._append_html(self._continuation_prompt_html)
238 243 self._append_plain_text(lines[i])
244 cursor.endEditBlock()
239 245 self._control.moveCursor(QtGui.QTextCursor.End)
240 246
241 247 input_buffer = property(_get_input_buffer, _set_input_buffer)
@@ -392,12 +398,14 b' class ConsoleWidget(QtGui.QWidget):'
392 398 ANSI codes if enabled.
393 399 """
394 400 cursor = self._get_end_cursor()
401 cursor.beginEditBlock()
395 402 if self.ansi_codes:
396 403 for substring in self._ansi_processor.split_string(text):
397 404 format = self._ansi_processor.get_format()
398 405 cursor.insertText(substring, format)
399 406 else:
400 407 cursor.insertText(text)
408 cursor.endEditBlock()
401 409
402 410 def _append_plain_text_keeping_prompt(self, text):
403 411 """ Writes 'text' after the current prompt, then restores the old prompt
@@ -490,8 +498,8 b' class ConsoleWidget(QtGui.QWidget):'
490 498 intercepted = True
491 499
492 500 elif ctrl_down:
493 if key == QtCore.Qt.Key_C and self._executing:
494 intercepted = self._execute_interrupt()
501 if key == QtCore.Qt.Key_C:
502 intercepted = self._executing and self._execute_interrupt()
495 503
496 504 elif key == QtCore.Qt.Key_K:
497 505 if self._in_buffer(position):
@@ -563,7 +571,7 b' class ConsoleWidget(QtGui.QWidget):'
563 571 intercepted = not self._in_buffer(position - 1)
564 572
565 573 elif key == QtCore.Qt.Key_Home:
566 cursor.movePosition(QtGui.QTextCursor.StartOfLine)
574 cursor.movePosition(QtGui.QTextCursor.StartOfBlock)
567 575 start_line = cursor.blockNumber()
568 576 if start_line == self._get_prompt_cursor().blockNumber():
569 577 start_pos = self._prompt_pos
@@ -576,15 +584,15 b' class ConsoleWidget(QtGui.QWidget):'
576 584 self._set_position(start_pos)
577 585 intercepted = True
578 586
579 elif key == QtCore.Qt.Key_Backspace and not alt_down:
587 elif key == QtCore.Qt.Key_Backspace:
580 588
581 589 # Line deletion (remove continuation prompt)
582 590 len_prompt = len(self._continuation_prompt)
583 591 if not self._reading and \
584 592 cursor.columnNumber() == len_prompt and \
585 593 position != self._prompt_pos:
586 cursor.setPosition(position - len_prompt,
587 QtGui.QTextCursor.KeepAnchor)
594 cursor.movePosition(QtGui.QTextCursor.StartOfBlock,
595 QtGui.QTextCursor.KeepAnchor)
588 596 cursor.removeSelectedText()
589 597
590 598 # Regular backwards deletion
@@ -733,10 +741,10 b' class ConsoleWidget(QtGui.QWidget):'
733 741 """
734 742 document = self._control.document()
735 743 position -= 1
736 while self._in_buffer(position) and \
744 while position >= self._prompt_pos and \
737 745 not document.characterAt(position).isLetterOrNumber():
738 746 position -= 1
739 while self._in_buffer(position) and \
747 while position >= self._prompt_pos and \
740 748 document.characterAt(position).isLetterOrNumber():
741 749 position -= 1
742 750 cursor = self._control.textCursor()
@@ -764,6 +772,7 b' class ConsoleWidget(QtGui.QWidget):'
764 772 """ Insert HTML using the specified cursor in such a way that future
765 773 formatting is unaffected.
766 774 """
775 cursor.beginEditBlock()
767 776 cursor.insertHtml(html)
768 777
769 778 # After inserting HTML, the text document "remembers" it's in "html
@@ -776,6 +785,7 b' class ConsoleWidget(QtGui.QWidget):'
776 785 cursor.removeSelectedText()
777 786 cursor.movePosition(QtGui.QTextCursor.Right)
778 787 cursor.insertText(' ', QtGui.QTextCharFormat())
788 cursor.endEditBlock()
779 789
780 790 def _insert_into_buffer(self, text):
781 791 """ Inserts text into the input buffer at the current cursor position,
@@ -799,19 +809,29 b' class ConsoleWidget(QtGui.QWidget):'
799 809 def _in_buffer(self, position):
800 810 """ Returns whether the given position is inside the editing region.
801 811 """
802 return position >= self._prompt_pos
812 cursor = self._control.textCursor()
813 cursor.setPosition(position)
814 line = cursor.blockNumber()
815 prompt_line = self._get_prompt_cursor().blockNumber()
816 if line == prompt_line:
817 return position >= self._prompt_pos
818 elif line > prompt_line:
819 cursor.movePosition(QtGui.QTextCursor.StartOfBlock)
820 prompt_pos = cursor.position() + len(self._continuation_prompt)
821 return position >= prompt_pos
822 return False
803 823
804 824 def _keep_cursor_in_buffer(self):
805 825 """ Ensures that the cursor is inside the editing region. Returns
806 826 whether the cursor was moved.
807 827 """
808 828 cursor = self._control.textCursor()
809 if cursor.position() < self._prompt_pos:
829 if self._in_buffer(cursor.position()):
830 return False
831 else:
810 832 cursor.movePosition(QtGui.QTextCursor.End)
811 833 self._control.setTextCursor(cursor)
812 834 return True
813 else:
814 return False
815 835
816 836 def _prompt_started(self):
817 837 """ Called immediately after a new prompt is displayed.
@@ -261,7 +261,7 b' class FrontendWidget(HistoryConsoleWidget):'
261 261 """
262 262 if cursor is None:
263 263 cursor = self._get_cursor()
264 cursor.movePosition(QtGui.QTextCursor.StartOfLine,
264 cursor.movePosition(QtGui.QTextCursor.StartOfBlock,
265 265 QtGui.QTextCursor.KeepAnchor)
266 266 text = str(cursor.selection().toPlainText())
267 267 return self._completion_lexer.get_context(text)
General Comments 0
You need to be logged in to leave comments. Login now