Function: ruby-smie-rules

ruby-smie-rules is a byte-compiled function defined in ruby-mode.el.gz.

Signature

(ruby-smie-rules KIND TOKEN)

Source Code

;; Defined in /usr/src/emacs/lisp/progmodes/ruby-mode.el.gz
(defun ruby-smie-rules (kind token)
  (pcase (cons kind token)
    ('(:elem . basic) ruby-indent-level)
    ;; "foo" "bar" is the concatenation of the two strings, so the second
    ;; should be aligned with the first.
    ('(:elem . args) (if (looking-at "\\s\"") 0))
    ;; (`(:after . ",") (smie-rule-separator kind))
    ('(:before . ";")
     (cond
      ((smie-rule-parent-p "def" "begin" "do" "class" "module" "for"
                           "while" "until" "unless"
                           "if" "then" "elsif" "else" "when" "in"
                           "rescue" "ensure" "{")
       (smie-rule-parent ruby-indent-level))
      ;; For (invalid) code between switch and case.
      ;; (if (smie-parent-p "switch") 4)
      ))
    (`(:before . ,(or "(" "[" "{"))
     (cond
      ((and (not (eq ruby-bracketed-args-indent t))
            (smie-rule-prev-p "," "(" "["))
       (cons 'column (current-indentation)))
      ((and (equal token "{")
            (not (smie-rule-prev-p "(" "{" "[" "," "=>" "=" "return" ";" "do"))
            (save-excursion
              (forward-comment -1)
              (not (eq (preceding-char) ?:))))
       ;; Curly block opener.
       (if ruby-block-indent
           (ruby-smie--indent-to-stmt)
         (cons 'column (current-indentation))))
      ((smie-rule-hanging-p)
       ;; Treat purely syntactic block-constructs as being part of their parent,
       ;; when the opening token is hanging and the parent is not an
       ;; open-paren.
       (cond
        ((eq (car (smie-indent--parent)) t) nil)
        ;; When after `.', let's always de-indent,
        ;; because when `.' is inside the line, the
        ;; additional indentation from it looks out of place.
        ((smie-rule-parent-p ".")
         ;; Traverse up the call chain until the parent is not `.',
         ;; or `.' at indentation, or at eol.
         (while (and (not (ruby-smie--bosp))
                     (equal (nth 2 (smie-backward-sexp ".")) ".")
                     (not (ruby-smie--bosp)))
           (forward-char -1))
         (smie-indent-virtual))
        ((save-excursion
           (and (smie-rule-parent-p " @ ")
                (goto-char (nth 1 (smie-indent--parent)))
                (smie-rule-prev-p "def=")
                (cons 'column (- (current-column) 3)))))
        (t (smie-rule-parent))))))
    (`(:after . ,(or "(" "[" "{"))
     ;; FIXME: Shouldn't this be the default behavior of
     ;; `smie-indent-after-keyword'?
     (save-excursion
       (forward-char 1)
       (skip-chars-forward " \t")
       ;; `smie-rule-hanging-p' is not good enough here,
       ;; because we want to reject hanging tokens at bol, too.
       (unless (or (eolp) (forward-comment 1))
         (cons 'column (current-column)))))
    ('(:before . " @ ")
     (cond
      ((and (not ruby-parenless-call-arguments-indent)
            (not (smie-rule-parent-p "def" "def=")))
       (ruby-smie--indent-to-stmt ruby-indent-level))
      ((or (eq ruby-method-params-indent t)
           (not (smie-rule-parent-p "def" "def=")))
       (save-excursion
         (skip-chars-forward " \t")
         (cons 'column (current-column))))
      (t (smie-rule-parent (or ruby-method-params-indent 0)))))
    ('(:before . "do")
     (if ruby-block-indent
         (ruby-smie--indent-to-stmt)
       (cons 'column (current-indentation))))
    ('(:before . ".")
     (if (smie-rule-sibling-p)
         (when ruby-align-chained-calls
           (while
               (let ((pos (point))
                     (parent (smie-backward-sexp ".")))
                 (if (not (equal (nth 2 parent) "."))
                     (progn (goto-char pos) nil)
                   (goto-char (nth 1 parent))
                   (not (smie-rule-bolp)))))
           (cons 'column (current-column)))
       (smie-backward-sexp ".")
       (if ruby-method-call-indent
           (cons 'column (+ (current-column)
                            ruby-indent-level))
         (ruby-smie--indent-to-stmt ruby-indent-level))))
    (`(:before . ,(or "else" "then" "elsif" "rescue" "ensure"))
     (smie-rule-parent))
    (`(:before . ,(or "when" "in"))
     ;; Align to the previous `when', but look up the virtual
     ;; indentation of `case'.
     (if (smie-rule-sibling-p) 0 (smie-rule-parent)))
    (`(:after . ,(or "=" "+" "-" "*" "/" "&&" "||" "%" "**" "^" "&"
                     "<=>" ">" "<" ">=" "<=" "==" "===" "!=" "<<" ">>"
                     "+=" "-=" "*=" "/=" "%=" "**=" "&=" "|=" "^=" "|"
                     "<<=" ">>=" "&&=" "||=" "and" "or"))
     (cond
      ((not ruby-after-operator-indent)
       (ruby-smie--indent-to-stmt (if (smie-indent--hanging-p)
                                      ruby-indent-level
                                    0)))
      ((and (smie-rule-parent-p ";" nil)
            (smie-indent--hanging-p))
       ruby-indent-level)))
    (`(:before . "=")
     (or
      (save-excursion
        (and (smie-rule-parent-p " @ ")
             (goto-char (nth 1 (smie-indent--parent)))
             (smie-rule-prev-p "def=")
             (cons 'column (+ (current-column) ruby-indent-level -3))))
      (and (smie-rule-parent-p ",")
           (smie-rule-parent))))
    (`(:after . ,(or "?" ":"))
     (if ruby-after-operator-indent
         ruby-indent-level
       (ruby-smie--indent-to-stmt ruby-indent-level)))
    (`(:before . ,(guard (memq (intern-soft token) ruby-alignable-keywords)))
     (when (not (ruby--at-indentation-p))
       (if (ruby-smie--indent-to-stmt-p token)
           (ruby-smie--indent-to-stmt)
         (cons 'column (current-column)))))
    ('(:before . "iuwu-mod")
     (smie-rule-parent ruby-indent-level))
    (`(:before . ",")
     (and (not ruby-parenless-call-arguments-indent)
          (smie-rule-parent-p " @ ")
          (ruby-smie--indent-to-stmt ruby-indent-level)))))