Show More
@@ -109,7 +109,7 b' class WxConsoleView(stc.StyledTextCtrl):' | |||||
109 |
|
109 | |||
110 | def __init__(self,parent,prompt,intro="",background_color="BLACK", |
|
110 | def __init__(self,parent,prompt,intro="",background_color="BLACK", | |
111 | pos=wx.DefaultPosition, ID = -1, size=wx.DefaultSize, |
|
111 | pos=wx.DefaultPosition, ID = -1, size=wx.DefaultSize, | |
112 | style=0): |
|
112 | style=0, autocomplete_mode = 'IPYTHON'): | |
113 | ''' |
|
113 | ''' | |
114 | Initialize console view. |
|
114 | Initialize console view. | |
115 |
|
115 | |||
@@ -121,6 +121,9 b' class WxConsoleView(stc.StyledTextCtrl):' | |||||
121 | @param background_color: Can be BLACK or WHITE |
|
121 | @param background_color: Can be BLACK or WHITE | |
122 | @type background_color: string |
|
122 | @type background_color: string | |
123 | @param other: init param of styledTextControl (can be used as-is) |
|
123 | @param other: init param of styledTextControl (can be used as-is) | |
|
124 | @param autocomplete_mode: Can be 'IPYTHON' or 'STC' | |||
|
125 | 'IPYTHON' show autocompletion the ipython way | |||
|
126 | 'STC" show it scintilla text control way | |||
124 | ''' |
|
127 | ''' | |
125 | stc.StyledTextCtrl.__init__(self, parent, ID, pos, size, style) |
|
128 | stc.StyledTextCtrl.__init__(self, parent, ID, pos, size, style) | |
126 |
|
129 | |||
@@ -212,9 +215,11 b' class WxConsoleView(stc.StyledTextCtrl):' | |||||
212 | self.write(intro) |
|
215 | self.write(intro) | |
213 | self.setPrompt(prompt) |
|
216 | self.setPrompt(prompt) | |
214 | self.showPrompt() |
|
217 | self.showPrompt() | |
|
218 | ||||
|
219 | self.autocomplete_mode = autocomplete_mode | |||
215 |
|
220 | |||
216 | self.Bind(wx.EVT_KEY_DOWN, self._onKeypress, self) |
|
221 | self.Bind(wx.EVT_KEY_DOWN, self._onKeypress, self) | |
217 |
|
222 | |||
218 | def asyncWrite(self, text): |
|
223 | def asyncWrite(self, text): | |
219 | ''' |
|
224 | ''' | |
220 | Write given text to buffer in an asynchroneous way. |
|
225 | Write given text to buffer in an asynchroneous way. | |
@@ -353,33 +358,52 b' class WxConsoleView(stc.StyledTextCtrl):' | |||||
353 | def writeHistory(self,history): |
|
358 | def writeHistory(self,history): | |
354 | self.removeFromTo(self.getCurrentPromptStart(),self.getCurrentLineEnd()) |
|
359 | self.removeFromTo(self.getCurrentPromptStart(),self.getCurrentLineEnd()) | |
355 | self.changeLine(history) |
|
360 | self.changeLine(history) | |
|
361 | ||||
|
362 | def setCompletionMethod(self, completion): | |||
|
363 | if completion in ['IPYTHON','STC']: | |||
|
364 | self.autocomplete_mode = completion | |||
|
365 | else: | |||
|
366 | raise AttributeError | |||
|
367 | ||||
|
368 | def getCompletionMethod(self, completion): | |||
|
369 | return self.autocomplete_mode | |||
356 |
|
370 | |||
357 | def writeCompletion(self, possibilities): |
|
371 | def writeCompletion(self, possibilities): | |
358 | max_len = len(max(possibilities,key=len)) |
|
372 | if self.autocomplete_mode == 'IPYTHON': | |
359 | max_symbol =' '*max_len |
|
373 | max_len = len(max(possibilities,key=len)) | |
360 |
|
374 | max_symbol =' '*max_len | ||
361 | #now we check how much symbol we can put on a line... |
|
375 | ||
362 | cursor_pos = self.getCursorPos() |
|
376 | #now we check how much symbol we can put on a line... | |
363 | test_buffer = max_symbol + ' '*4 |
|
377 | cursor_pos = self.getCursorPos() | |
364 | current_lines = self.GetLineCount() |
|
378 | test_buffer = max_symbol + ' '*4 | |
365 |
|
379 | current_lines = self.GetLineCount() | ||
366 | allowed_symbols = 80/len(test_buffer) |
|
380 | ||
367 |
|
|
381 | allowed_symbols = 80/len(test_buffer) | |
368 |
|
|
382 | if allowed_symbols == 0: | |
|
383 | allowed_symbols = 1 | |||
|
384 | ||||
|
385 | pos = 1 | |||
|
386 | buf = '' | |||
|
387 | for symbol in possibilities: | |||
|
388 | #buf += symbol+'\n'#*spaces) | |||
|
389 | if pos<allowed_symbols: | |||
|
390 | spaces = max_len - len(symbol) + 4 | |||
|
391 | buf += symbol+' '*spaces | |||
|
392 | pos += 1 | |||
|
393 | else: | |||
|
394 | buf+=symbol+'\n' | |||
|
395 | pos = 1 | |||
|
396 | self.write(buf) | |||
|
397 | else: | |||
|
398 | possibilities.sort() # Python sorts are case sensitive | |||
|
399 | self.AutoCompSetIgnoreCase(False) | |||
|
400 | #let compute the length ot last word | |||
|
401 | splitter = [' ','(','[','{'] | |||
|
402 | last_word = self.getCurrentLine() | |||
|
403 | for breaker in splitter: | |||
|
404 | last_word = last_word.split(breaker)[-1] | |||
|
405 | self.AutoCompShow(len(last_word), " ".join(possibilities)) | |||
369 |
|
406 | |||
370 | pos = 1 |
|
|||
371 | buf = '' |
|
|||
372 | for symbol in possibilities: |
|
|||
373 | #buf += symbol+'\n'#*spaces) |
|
|||
374 | if pos<allowed_symbols: |
|
|||
375 | spaces = max_len - len(symbol) + 4 |
|
|||
376 | buf += symbol+' '*spaces |
|
|||
377 | pos += 1 |
|
|||
378 | else: |
|
|||
379 | buf+=symbol+'\n' |
|
|||
380 | pos = 1 |
|
|||
381 | self.write(buf) |
|
|||
382 |
|
||||
383 | def _onKeypress(self, event, skip=True): |
|
407 | def _onKeypress(self, event, skip=True): | |
384 | ''' |
|
408 | ''' | |
385 | Key press callback used for correcting behavior for console-like |
|
409 | Key press callback used for correcting behavior for console-like | |
@@ -394,41 +418,45 b' class WxConsoleView(stc.StyledTextCtrl):' | |||||
394 | @return: Return True if event as been catched. |
|
418 | @return: Return True if event as been catched. | |
395 | @rtype: boolean |
|
419 | @rtype: boolean | |
396 | ''' |
|
420 | ''' | |
397 | if event.GetKeyCode() == wx.WXK_HOME: |
|
|||
398 | if event.Modifiers == wx.MOD_NONE: |
|
|||
399 | self.moveCursorOnNewValidKey() |
|
|||
400 | self.moveCursor(self.getCurrentPromptStart()) |
|
|||
401 | return True |
|
|||
402 | elif event.Modifiers == wx.MOD_SHIFT: |
|
|||
403 | self.moveCursorOnNewValidKey() |
|
|||
404 | self.selectFromTo(self.getCurrentPromptStart(),self.getCursorPos()) |
|
|||
405 | return True |
|
|||
406 | else: |
|
|||
407 | return False |
|
|||
408 |
|
421 | |||
409 | elif event.GetKeyCode() == wx.WXK_LEFT: |
|
422 | if not self.AutoCompActive(): | |
410 |
if event. |
|
423 | if event.GetKeyCode() == wx.WXK_HOME: | |
411 | self.moveCursorOnNewValidKey() |
|
424 | if event.Modifiers == wx.MOD_NONE: | |
412 |
|
425 | self.moveCursorOnNewValidKey() | ||
413 | self.moveCursor(self.getCursorPos()-1) |
|
|||
414 | if self.getCursorPos() < self.getCurrentPromptStart(): |
|
|||
415 | self.moveCursor(self.getCurrentPromptStart()) |
|
426 | self.moveCursor(self.getCurrentPromptStart()) | |
|
427 | return True | |||
|
428 | elif event.Modifiers == wx.MOD_SHIFT: | |||
|
429 | self.moveCursorOnNewValidKey() | |||
|
430 | self.selectFromTo(self.getCurrentPromptStart(),self.getCursorPos()) | |||
|
431 | return True | |||
|
432 | else: | |||
|
433 | return False | |||
|
434 | ||||
|
435 | elif event.GetKeyCode() == wx.WXK_LEFT: | |||
|
436 | if event.Modifiers == wx.MOD_NONE: | |||
|
437 | self.moveCursorOnNewValidKey() | |||
|
438 | ||||
|
439 | self.moveCursor(self.getCursorPos()-1) | |||
|
440 | if self.getCursorPos() < self.getCurrentPromptStart(): | |||
|
441 | self.moveCursor(self.getCurrentPromptStart()) | |||
|
442 | return True | |||
|
443 | ||||
|
444 | elif event.GetKeyCode() == wx.WXK_BACK: | |||
|
445 | self.moveCursorOnNewValidKey() | |||
|
446 | if self.getCursorPos() > self.getCurrentPromptStart(): | |||
|
447 | event.Skip() | |||
416 | return True |
|
448 | return True | |
417 |
|
449 | |||
418 | elif event.GetKeyCode() == wx.WXK_BACK: |
|
450 | if skip: | |
419 | self.moveCursorOnNewValidKey() |
|
451 | if event.GetKeyCode() not in [wx.WXK_PAGEUP,wx.WXK_PAGEDOWN] and event.Modifiers == wx.MOD_NONE: | |
420 | if self.getCursorPos() > self.getCurrentPromptStart(): |
|
452 | self.moveCursorOnNewValidKey() | |
|
453 | ||||
421 | event.Skip() |
|
454 | event.Skip() | |
422 | return True |
|
455 | return True | |
423 |
|
456 | return False | ||
424 |
|
|
457 | else: | |
425 | if event.GetKeyCode() not in [wx.WXK_PAGEUP,wx.WXK_PAGEDOWN] and event.Modifiers == wx.MOD_NONE: |
|
|||
426 | self.moveCursorOnNewValidKey() |
|
|||
427 |
|
||||
428 | event.Skip() |
|
458 | event.Skip() | |
429 |
|
|
459 | ||
430 | return False |
|
|||
431 |
|
||||
432 | def OnUpdateUI(self, evt): |
|
460 | def OnUpdateUI(self, evt): | |
433 | # check for matching braces |
|
461 | # check for matching braces | |
434 | braceAtCaret = -1 |
|
462 | braceAtCaret = -1 | |
@@ -515,12 +543,24 b' class IPShellWidget(wx.Panel):' | |||||
515 | background_color=background_color) |
|
543 | background_color=background_color) | |
516 |
|
544 | |||
517 | self.cout.write = self.text_ctrl.asyncWrite |
|
545 | self.cout.write = self.text_ctrl.asyncWrite | |
|
546 | ||||
|
547 | self.completion_option = wx.CheckBox(self, -1, "Scintilla completion") | |||
|
548 | self.completion_option.SetValue(False) | |||
|
549 | option_text = wx.StaticText(self,-1,'Options:') | |||
518 |
|
550 | |||
519 | self.text_ctrl.Bind(wx.EVT_KEY_DOWN, self.keyPress) |
|
551 | self.text_ctrl.Bind(wx.EVT_KEY_DOWN, self.keyPress) | |
520 |
|
552 | self.Bind(wx.EVT_CHECKBOX, self.evtCheckOptionCompletion, self.completion_option) | ||
|
553 | ||||
521 | ### making the layout of the panel ### |
|
554 | ### making the layout of the panel ### | |
522 | sizer = wx.BoxSizer(wx.VERTICAL) |
|
555 | sizer = wx.BoxSizer(wx.VERTICAL) | |
523 | sizer.Add(self.text_ctrl, 1, wx.EXPAND) |
|
556 | sizer.Add(self.text_ctrl, 1, wx.EXPAND) | |
|
557 | option_sizer = wx.BoxSizer(wx.HORIZONTAL) | |||
|
558 | sizer.Add(option_sizer,0) | |||
|
559 | option_sizer.AddMany([(10,15), | |||
|
560 | option_text, | |||
|
561 | (20,15), | |||
|
562 | self.completion_option | |||
|
563 | ]) | |||
524 | self.SetAutoLayout(True) |
|
564 | self.SetAutoLayout(True) | |
525 | sizer.Fit(self) |
|
565 | sizer.Fit(self) | |
526 | sizer.SetSizeHints(self) |
|
566 | sizer.SetSizeHints(self) | |
@@ -630,12 +670,20 b' class IPShellWidget(wx.Panel):' | |||||
630 | autocompletions, etc. |
|
670 | autocompletions, etc. | |
631 | ''' |
|
671 | ''' | |
632 | if event.GetKeyCode() == ord('C'): |
|
672 | if event.GetKeyCode() == ord('C'): | |
633 | if event.Modifiers == wx.MOD_CONTROL: |
|
673 | if event.Modifiers == wx.MOD_CONTROL or event.Modifiers == wx.MOD_ALT: | |
634 | if self.cur_state == 'WAIT_END_OF_EXECUTION': |
|
674 | if self.cur_state == 'WAIT_END_OF_EXECUTION': | |
635 | #we raise an exception inside the IPython thread container |
|
675 | #we raise an exception inside the IPython thread container | |
636 | self.IP.ce.raise_exc(KeyboardInterrupt) |
|
676 | self.IP.ce.raise_exc(KeyboardInterrupt) | |
637 | return |
|
677 | return | |
638 |
|
678 | |||
|
679 | #let this before 'wx.WXK_RETURN' because we have to put 'IDLE' | |||
|
680 | #mode if AutoComp has been set as inactive | |||
|
681 | if self.cur_state == 'COMPLETING': | |||
|
682 | if not self.text_ctrl.AutoCompActive(): | |||
|
683 | self.cur_state = 'IDLE' | |||
|
684 | else: | |||
|
685 | event.Skip() | |||
|
686 | ||||
639 | if event.KeyCode == wx.WXK_RETURN: |
|
687 | if event.KeyCode == wx.WXK_RETURN: | |
640 | if self.cur_state == 'IDLE': |
|
688 | if self.cur_state == 'IDLE': | |
641 | #we change the state ot the state machine |
|
689 | #we change the state ot the state machine | |
@@ -663,7 +711,7 b' class IPShellWidget(wx.Panel):' | |||||
663 |
|
711 | |||
664 | if self.cur_state == 'WAITING_USER_INPUT': |
|
712 | if self.cur_state == 'WAITING_USER_INPUT': | |
665 | event.Skip() |
|
713 | event.Skip() | |
666 |
|
714 | |||
667 | if self.cur_state == 'IDLE': |
|
715 | if self.cur_state == 'IDLE': | |
668 | if event.KeyCode == wx.WXK_UP: |
|
716 | if event.KeyCode == wx.WXK_UP: | |
669 | history = self.IP.historyBack() |
|
717 | history = self.IP.historyBack() | |
@@ -680,17 +728,30 b' class IPShellWidget(wx.Panel):' | |||||
680 | return |
|
728 | return | |
681 | completed, possibilities = self.IP.complete(self.text_ctrl.getCurrentLine()) |
|
729 | completed, possibilities = self.IP.complete(self.text_ctrl.getCurrentLine()) | |
682 | if len(possibilities) > 1: |
|
730 | if len(possibilities) > 1: | |
683 |
|
|
731 | if self.text_ctrl.autocomplete_mode == 'IPYTHON': | |
684 |
self.text_ctrl. |
|
732 | cur_slice = self.text_ctrl.getCurrentLine() | |
685 |
self.text_ctrl.write |
|
733 | self.text_ctrl.write('\n') | |
686 |
self.text_ctrl.write( |
|
734 | self.text_ctrl.writeCompletion(possibilities) | |
687 |
|
735 | self.text_ctrl.write('\n') | ||
688 | self.text_ctrl.showPrompt() |
|
736 | ||
689 |
self.text_ctrl. |
|
737 | self.text_ctrl.showPrompt() | |
690 |
self.text_ctrl. |
|
738 | self.text_ctrl.write(cur_slice) | |
691 |
|
739 | self.text_ctrl.changeLine(completed or cur_slice) | ||
|
740 | else: | |||
|
741 | self.cur_state = 'COMPLETING' | |||
|
742 | self.text_ctrl.writeCompletion(possibilities) | |||
|
743 | else: | |||
|
744 | self.text_ctrl.changeLine(completed or cur_slice) | |||
692 | return |
|
745 | return | |
693 | event.Skip() |
|
746 | event.Skip() | |
|
747 | ||||
|
748 | #------------------------ Option Section --------------------------------- | |||
|
749 | def evtCheckOptionCompletion(self, event): | |||
|
750 | if event.IsChecked(): | |||
|
751 | self.text_ctrl.setCompletionMethod('STC') | |||
|
752 | else: | |||
|
753 | self.text_ctrl.setCompletionMethod('IPYTHON') | |||
|
754 | self.text_ctrl.SetFocus() | |||
694 |
|
755 | |||
695 | #------------------------ Hook Section ----------------------------------- |
|
756 | #------------------------ Hook Section ----------------------------------- | |
696 | def updateHistoryTracker(self,command_line): |
|
757 | def updateHistoryTracker(self,command_line): |
General Comments 0
You need to be logged in to leave comments.
Login now