Class: Ruber::AutoEnd::Extension
- Inherits:
-
Qt::Object
- Object
- Qt::Object
- Ruber::AutoEnd::Extension
- Includes:
- Extension
- Defined in:
- plugins/auto_end/auto_end.rb
Overview
Extension object for the Auto End plugin
The procedure of inserting an end
is split in two parts, performed in separate
moments:
- finding out whether the current line needs an end inserted after it. This is done in response to the Document#text_inserted signal
- inserting the text. This is done in response to the Document#text_changed signal
The reason for this two-step behaviour is that Document#text_inserted is emitted
multiple times in case of a Paste operation. Thus, inserting the end
keywords
in it would cause them to be added in the middle of the pasted text, which is
wrong. What we do instead is to analyze each line in response to Document#text_inserted,
storing the line position and the text to insert if appropriate, overwriting any
other information so that only the last position is recorded. When all text has
been processed, the document emits the Document#text_changed signal and, in response
to this we insert the end keyword (if appropriate).
Defined Under Namespace
Classes: Insertion
Constant Summary
- IDENTIFIER_PATTERN =
The regexp fragment which matches an identifier. In theory, this should just be
\w+
. However, from ruby 1.9.2,\w
only matches ASCII characters, while identifiers can also contain unicode characters. To allow for this, the\p{Word}
character class is used from ruby 1.9.2 onward, while\w
is used for previous versions RUBY_VERSION >= '1.9.2' ? '\p{Word}+' : '\w+'
- MULTI_ID_PATTERN =
The regexp fragment which matches a multiple identifier (that is, an identifier maybe followed by several other identifiers separated by
::
) "#{IDENTIFIER_PATTERN}(?:::#{IDENTIFIER_PATTERN})*"
- PATTERNS =
The patterns used to find out whether an
end
keyword should be inserted after a line.Each entry is itself an array with three elements:
- the regexp to match agains the line
- the text to insert if the regexp match
- an array with two elements, representing the position where the cursor should be moved to after the insertion, as described in Insertion#final_position
[ [/^\s*if\s/, "\nend", [0, -1]], [/=\s*if\s/, "\nend", [0, -1]], [/^\s*unless\s/, "\nend", [0, -1]], [/=\s*unless\s/, "\nend", [0, -1]], [/\bdo\s*$/, "\nend", [0, -1]], [/\bdo\s+\|/, "\nend", [0, -1]], [/^\s*def\s/, "\nend", [0, -1]], [/\bclass\b/, "\nend", [0, -1]], [/\bmodule\b/, "\nend", [0, -1]], [/^\s*case\b/, "\nend", [0, -1]], [/=\s*case\b/, "\nend", [0, -1]], [/^\s*while\s/, "\nend", [0,-1]], [/^\s*until\s/, "\nend", [0,-1]], [/^=begin(\s|$)/, "\n=end", [0, -1]], [/^\s*begin\s/, "\nend", [0, -1]], [/(^=\s+|.=\s*)begin\s/, "\nend", [0, -1]], [/^\s*for\s/, "\nend", [0,-1]], [/=\s*for\s/, "\nend", [0,-1]] ]
Instance Attribute Summary
Attributes included from Extension
Instance Method Summary (collapse)
-
- (nil) connect_slots
private
Makes connections to the document’s signals.
-
- (nil) disconnect_slots
private
Disconnects connections to the document’s signals.
-
- (Extension) initialize(prj)
constructor
A new instance of Extension.
-
- (Object) insert_text(insert_pos, lines, dest)
private
Inserts text at the given position and moves the cursor to the specified position.
-
- (nil) remove_from_project
private
Override of #remove_from_project.
-
- (nil) text_changed
slot
private
Slot called in response to the Document#text_changed signal.
-
- (Object) text_inserted(range)
slot
private
Slot called when some text is inserted.
Methods included from Extension
#query_close, #save_settings, #shutdown
Constructor Details
- (Extension) initialize(prj)
A new instance of Extension
130 131 132 133 134 135 |
# File 'plugins/auto_end/auto_end.rb', line 130 def initialize prj super @doc = prj.document @insertion = nil connect_slots end |
Instance Method Details
- (nil) connect_slots (private)
Makes connections to the document’s signals
199 200 201 202 203 |
# File 'plugins/auto_end/auto_end.rb', line 199 def connect_slots connect @doc, SIGNAL('text_inserted(KTextEditor::Range, QObject*)'), self, SLOT('text_inserted(KTextEditor::Range)') connect @doc, SIGNAL('text_changed(QObject*)'), self, SLOT(:text_changed) nil end |
- (nil) disconnect_slots (private)
Disconnects connections to the document’s signals
209 210 211 212 |
# File 'plugins/auto_end/auto_end.rb', line 209 def disconnect_slots disconnect @doc, SIGNAL('text_inserted(KTextEditor::Range, QObject*)'), self, SLOT('text_inserted(KTextEditor::Range)') disconnect @doc, SIGNAL('text_changed(QObject*)'), self, SLOT(:text_changed) end |
- (Object) insert_text(insert_pos, lines, dest) (private)
nothing is done unless the active view (according to Document#active_view) is associated with the document
Inserts text at the given position and moves the cursor to the specified position
To avoid the possibility of infinite recursion, before inserting text #disconnect_slots is called. After the text has been inserted #connect_slots is called.
227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 |
# File 'plugins/auto_end/auto_end.rb', line 227 def insert_text insert_pos, lines, dest view = @doc.active_view return unless view disconnect_slots replace_pos = KTextEditor::Cursor.new insert_pos.line, @doc.line_length(insert_pos.line) insert_pos.column = @doc.line_length insert_pos.line @doc.insert_text insert_pos, lines final_pos = KTextEditor::Cursor.new insert_pos.line + lines.size - 1, lines[-1].size view.execute_action 'tools_align' dest_line = insert_pos.line+dest[0] dest_col = dest[1] dest_col += @doc.line_length(dest_line) + 1 if dest_col < 0 view.go_to dest_line, dest_col connect_slots end |
- (nil) remove_from_project (private)
Override of #remove_from_project
191 192 193 |
# File 'plugins/auto_end/auto_end.rb', line 191 def remove_from_project disconnect_slots end |
- (nil) text_changed (private)
Slot called in response to the Document#text_changed signal
If there’s an insertion position memorized, inserts the corresponding text after the current line, then moves the cursor to the position stored with the insertion object.
The current insertion is forgotten.
178 179 180 181 182 183 184 |
# File 'plugins/auto_end/auto_end.rb', line 178 def text_changed if @insertion insert_text KTextEditor::Cursor.new(@insertion.line_number, 0), @insertion.lines, @insertion.final_position @insertion = nil end end |
Slot Signature:
text_changed()
- (Object) text_inserted(range) (private)
Slot called when some text is inserted
If one of the recognized patterns match the current line, memorizes an Insertion object pointing to the current line and using the parameters associated with the matching pattern.
If the inserted text doesn’t end in a newline, nothing is done.
If the current line doesn’t match any pattern, the currently memorized insertion position (if any) is forgotten
151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 |
# File 'plugins/auto_end/auto_end.rb', line 151 def text_inserted range return unless @doc.active? text = @doc.text range return unless text.end_with? "\n" @insertion = nil line = @doc.line( range.end.line - 1) pattern = PATTERNS.find{|pat| pat[0].match line} if pattern and !line.start_with? '#' check_res = @doc.extension(:syntax_checker).check_syntax(:format => false, :update => false) return unless check_res errors = check_res[:errors] # Usually, missing end errors are the last ones to be reported if errors && !errors.empty? && errors[-1].error_type == :missing_end # indentation = line.match(/^\s*/)[0].size # next_indentation = @doc.line(range.end.line + 1).match(/^\s*/)[0].size # unless next_indentation > indentation @insertion = Insertion.new range.end.line, pattern[1], pattern[2] end end nil end |
Slot Signature:
text_inserted(KTextEditor::Range)