Class: SyntaxTree::Statements
Overview
Everything that has a block of code inside of it has a list of statements. Normally we would just track those as a node that has an array body, but we have some special handling in order to handle empty statement lists. They need to have the right location information, so all of the parent node of stmts nodes will report back down the location information. We then propagate that onto void_stmt nodes inside the stmts in order to make sure all comments get printed appropriately.
Instance Attribute Summary collapse
-
#body ⇒ Object
readonly
- Array[ untyped ]
-
the list of expressions contained within this node.
-
#comments ⇒ Object
readonly
- Array[ Comment | EmbDoc ]
-
the comments attached to this node.
-
#parser ⇒ Object
readonly
- SyntaxTree
-
the parser that is generating this node.
Attributes inherited from Node
Instance Method Summary collapse
- #===(other) ⇒ Object
- #accept(visitor) ⇒ Object
- #bind(start_char, start_column, end_char, end_column) ⇒ Object
- #bind_end(end_char, end_column) ⇒ Object
- #child_nodes ⇒ Object (also: #deconstruct)
- #copy(body: nil, location: nil) ⇒ Object
- #deconstruct_keys(_keys) ⇒ Object
- #empty? ⇒ Boolean
- #format(q) ⇒ Object
-
#initialize(parser, body:, location:) ⇒ Statements
constructor
A new instance of Statements.
Methods inherited from Node
#construct_keys, #pretty_print, #to_json
Constructor Details
#initialize(parser, body:, location:) ⇒ Statements
Returns a new instance of Statements.
9764 9765 9766 9767 9768 9769 |
# File 'lib/syntax_tree/node.rb', line 9764 def initialize(parser, body:, location:) @parser = parser @body = body @location = location @comments = [] end |
Instance Attribute Details
#body ⇒ Object (readonly)
- Array[ untyped ]
-
the list of expressions contained within this node
9759 9760 9761 |
# File 'lib/syntax_tree/node.rb', line 9759 def body @body end |
#comments ⇒ Object (readonly)
- Array[ Comment | EmbDoc ]
-
the comments attached to this node
9762 9763 9764 |
# File 'lib/syntax_tree/node.rb', line 9762 def comments @comments end |
#parser ⇒ Object (readonly)
- SyntaxTree
-
the parser that is generating this node
9756 9757 9758 |
# File 'lib/syntax_tree/node.rb', line 9756 def parser @parser end |
Instance Method Details
#===(other) ⇒ Object
9892 9893 9894 |
# File 'lib/syntax_tree/node.rb', line 9892 def ===(other) other.is_a?(Statements) && ArrayMatch.call(body, other.body) end |
#accept(visitor) ⇒ Object
9818 9819 9820 |
# File 'lib/syntax_tree/node.rb', line 9818 def accept(visitor) visitor.visit_statements(self) end |
#bind(start_char, start_column, end_char, end_column) ⇒ Object
9771 9772 9773 9774 9775 9776 9777 9778 9779 9780 9781 9782 9783 9784 9785 9786 9787 9788 9789 9790 9791 9792 9793 9794 9795 9796 9797 9798 |
# File 'lib/syntax_tree/node.rb', line 9771 def bind(start_char, start_column, end_char, end_column) @location = Location.new( start_line: location.start_line, start_char: start_char, start_column: start_column, end_line: location.end_line, end_char: end_char, end_column: end_column ) if body[0].is_a?(VoidStmt) location = body[0].location location = Location.new( start_line: location.start_line, start_char: start_char, start_column: start_column, end_line: location.end_line, end_char: start_char, end_column: end_column ) body[0] = VoidStmt.new(location: location) end attach_comments(start_char, end_char) end |
#bind_end(end_char, end_column) ⇒ Object
9800 9801 9802 9803 9804 9805 9806 9807 9808 9809 9810 |
# File 'lib/syntax_tree/node.rb', line 9800 def bind_end(end_char, end_column) @location = Location.new( start_line: location.start_line, start_char: location.start_char, start_column: location.start_column, end_line: location.end_line, end_char: end_char, end_column: end_column ) end |
#child_nodes ⇒ Object Also known as: deconstruct
9822 9823 9824 |
# File 'lib/syntax_tree/node.rb', line 9822 def child_nodes body end |
#copy(body: nil, location: nil) ⇒ Object
9826 9827 9828 9829 9830 9831 9832 9833 9834 9835 9836 |
# File 'lib/syntax_tree/node.rb', line 9826 def copy(body: nil, location: nil) node = Statements.new( parser, body: body || self.body, location: location || self.location ) node.comments.concat(comments.map(&:copy)) node end |
#deconstruct_keys(_keys) ⇒ Object
9840 9841 9842 |
# File 'lib/syntax_tree/node.rb', line 9840 def deconstruct_keys(_keys) { parser: parser, body: body, location: location, comments: comments } end |
#empty? ⇒ Boolean
9812 9813 9814 9815 9816 |
# File 'lib/syntax_tree/node.rb', line 9812 def empty? body.all? do |statement| statement.is_a?(VoidStmt) && statement.comments.empty? end end |
#format(q) ⇒ Object
9844 9845 9846 9847 9848 9849 9850 9851 9852 9853 9854 9855 9856 9857 9858 9859 9860 9861 9862 9863 9864 9865 9866 9867 9868 9869 9870 9871 9872 9873 9874 9875 9876 9877 9878 9879 9880 9881 9882 9883 9884 9885 9886 9887 9888 9889 9890 |
# File 'lib/syntax_tree/node.rb', line 9844 def format(q) line = nil # This handles a special case where you've got a block of statements where # the only value is a comment. In that case a lot of nodes like # brace_block will attempt to format as a single line, but since that # wouldn't work with a comment, we intentionally break the parent group. if body.length == 2 void_stmt, comment = body if void_stmt.is_a?(VoidStmt) && comment.is_a?(Comment) q.format(comment) q.break_parent return end end previous = nil body.each do |statement| next if statement.is_a?(VoidStmt) if line.nil? q.format(statement) elsif (statement.location.start_line - line) > 1 q.breakable_force q.breakable_force q.format(statement) elsif (statement.is_a?(VCall) && statement.access_control?) || (previous.is_a?(VCall) && previous.access_control?) q.breakable_force q.breakable_force q.format(statement) elsif statement.location.start_line != line q.breakable_force q.format(statement) elsif !q.parent.is_a?(StringEmbExpr) q.breakable_force q.format(statement) else q.text("; ") q.format(statement) end line = statement.location.end_line previous = statement end end |