changeset 20449:046904b54dc4

editor with smart indentation for octave files (bug #41554) * file-editor-tab.cc (file-editor-tab.cc): new class variables for line, column, changed lines and auto-indent setting, connect signal linesChanged to new slot; (notice_settings): get setting for auto-indent and store it in flag; (handle_lines_changed): new slot for changed lines, just storing this state in a flag; (handle_cursor_moved): if lines have changed check more conditions and call smart indentation; (do_smart_indent): do the smart indentation based on keyword in previous line * file-editor-tab.h: new class variables, new slot for chaned lines, new method for smart indentation
author Torsten <ttl@justmail.de>
date Sat, 01 Aug 2015 11:26:32 +0200
parents 2edd668e7784
children 57a3e21e131b
files libgui/src/m-editor/file-editor-tab.cc libgui/src/m-editor/file-editor-tab.h
diffstat 2 files changed, 82 insertions(+), 0 deletions(-) [+]
line wrap: on
line diff
--- a/libgui/src/m-editor/file-editor-tab.cc	Fri Jul 31 14:01:39 2015 +0200
+++ b/libgui/src/m-editor/file-editor-tab.cc	Sat Aug 01 11:26:32 2015 +0200
@@ -71,6 +71,7 @@
 {
   _lexer_apis = 0;
   _is_octave_file = true;
+  _lines_changed = false;
 
   _ced = directory_arg;
 
@@ -78,10 +79,15 @@
   _file_system_watcher.setObjectName ("_qt_autotest_force_engine_poller");
 
   _edit_area = new octave_qscintilla (this);
+  _line = 0;
+  _col  = 0;
 
   connect (_edit_area, SIGNAL (cursorPositionChanged (int, int)),
            this, SLOT (handle_cursor_moved (int,int)));
 
+  connect (_edit_area, SIGNAL (linesChanged ()),
+           this, SLOT (handle_lines_changed ()));
+
   connect (_edit_area, SIGNAL (context_menu_edit_signal (const QString&)),
            this, SLOT (handle_context_menu_edit (const QString&)));
 
@@ -1878,6 +1884,7 @@
 
   _edit_area->setAutoIndent
         (settings->value ("editor/auto_indent",true).toBool ());
+  _smart_indent = settings->value ("editor/auto_indent",true).toBool ();
   _edit_area->setTabIndents
         (settings->value ("editor/tab_indents_line",false).toBool ());
   _edit_area->setBackspaceUnindents
@@ -2063,15 +2070,82 @@
 }
 
 void
+file_editor_tab::handle_lines_changed ()
+{
+  // the related signal is emitted before cursor-move-signal!
+  _lines_changed = true;
+}
+
+void
 file_editor_tab::handle_cursor_moved (int line, int col)
 {
   if (_edit_area->SendScintilla (QsciScintillaBase::SCI_AUTOCACTIVE))
     show_auto_completion (this);
 
+  if (_lines_changed)  // check for smart indentation
+    {
+      _lines_changed = false;
+      if (_is_octave_file && _smart_indent && line == _line+1 && col < _col)
+        do_smart_indent ();
+    }
+
+  _line = line;
+  _col  = col;
+
   _row_indicator->setNum (line+1);
   _col_indicator->setNum (col+1);
 }
 
+void
+file_editor_tab::do_smart_indent ()
+{
+  QString prev_line = _edit_area->text (_line);
+
+  QRegExp bkey = QRegExp ("^[\t ]*(if|for|while|switch|case|do|function"
+                          "|unwind_protect|unwind_protect_cleanup|try)"
+                          "[\n\t #%]");
+  if (prev_line.contains (bkey))
+    {
+      _edit_area->indent (_line+1);
+      _edit_area->setCursorPosition (_line+1,
+                                     _edit_area->indentation (_line) +
+                                     _edit_area->indentationWidth ());
+      return;
+    }
+
+  QRegExp mkey = QRegExp ("^[\t ]*(else|elseif|catch)[\t #%\n]");
+  if (prev_line.contains (mkey))
+    {
+      int prev_ind = _edit_area->indentation (_line-1);
+      int act_ind = _edit_area->indentation (_line);
+
+      if (prev_ind == act_ind)
+        _edit_area->unindent (_line);
+      else if (prev_ind > act_ind)
+        {
+          _edit_area->setIndentation (_line+1, prev_ind);
+          _edit_area->setCursorPosition (_line+1, prev_ind);
+        }
+      return;
+    }
+
+  QRegExp ekey = QRegExp ("^[\t ]*(end|endif|endfor|endwhile|until|endfunction"
+                          "|end_try_catch|end_unwind_protext)[\t #%\n(;]");
+  if (prev_line.contains (ekey))
+    {
+      if (_edit_area->indentation (_line-1) <= _edit_area->indentation (_line))
+        {
+          _edit_area->unindent (_line+1);
+          _edit_area->unindent (_line);
+          _edit_area->setCursorPosition (_line+1,
+                                         _edit_area->indentation (_line));
+        }
+      return;
+    }
+
+}
+
+
 QString
 file_editor_tab::get_function_name ()
 {
--- a/libgui/src/m-editor/file-editor-tab.h	Fri Jul 31 14:01:39 2015 +0200
+++ b/libgui/src/m-editor/file-editor-tab.h	Sat Aug 01 11:26:32 2015 +0200
@@ -173,6 +173,7 @@
   void auto_margin_width ();
 
   void handle_cursor_moved (int line, int col);
+  void handle_lines_changed (void);
 
 private:
 
@@ -216,6 +217,8 @@
   void add_octave_apis (octave_value_list key_ovl);
   QString get_function_name ();
 
+  void do_smart_indent (void);
+
   QsciScintilla::EolMode detect_eol_mode ();
   void update_eol_indicator ();
 
@@ -236,6 +239,7 @@
   bool _copy_available;
   bool _is_octave_file;
   bool _always_reload_changed_files;
+  bool _smart_indent;
 
   QFileSystemWatcher _file_system_watcher;
 
@@ -247,6 +251,10 @@
   QString _prep_apis_file;
 
   static bool _cancelled;
+
+  int _line;
+  int _col;
+  bool _lines_changed;
 };
 
 #endif