emacs-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Indentation in the METAPOST mode.


From: Michaël Cadilhac
Subject: Re: Indentation in the METAPOST mode.
Date: Thu, 09 Aug 2007 15:22:31 +0200
User-agent: Gnus/5.110007 (No Gnus v0.7) Emacs/22.1.50 (gnu/linux)

address@hidden (Michaël Cadilhac) writes:

> Hi guys, long time no see !
>
> Indentation in the METAPOST mode has, IMO, two major flaws :
>
> 1. A bug. If the buffer starts with beginfig, the contents of the figure
> is not properly indented (it stays on the first column).
>
> 2. When wrapping an expression on several lines, the indentation is the
> same for each line, this is bad style : I'd prefer
>
> beginfig(1)
>   draw (0,0)--(1,2)--(10,3)--
>     (0,1)--(10,3);
>   draw (2,2);
> endfig
>
> I propose the following patch which considers that keywords like
> beginfig does not need ending semicolon (it's /quite/ the case).
>
> Tell me if it's worth installing it.

Please consider this extended version. It uses a complete other way to
deal with the indentation which suffers from less flaws. It still has
the following, however, with grouping :

  draw begingraph(3cm,2cm)
      setrange(whatever, 0, whatever, whatever);
    gdraw "data1";
    other-instruction;
  endgraph;

This is not that bad however. I've tested it with the 305 examples of
http://tex.loria.fr/prod-graph/zoonekynd/metapost/metapost.html
with great result.

Index: lisp/progmodes/meta-mode.el
===================================================================
RCS file: /sources/emacs/emacs/lisp/progmodes/meta-mode.el,v
retrieving revision 1.19
diff -c -r1.19 meta-mode.el
*** lisp/progmodes/meta-mode.el 26 Jul 2007 05:27:28 -0000      1.19
--- lisp/progmodes/meta-mode.el 9 Aug 2007 13:13:31 -0000
***************
*** 605,618 ****
  
  (defun meta-indent-calculate ()
    "Return the indentation of current line of Metafont or MetaPost source."
    (save-excursion
      (back-to-indentation)
      (cond
!       ;; Comments to the left margin.
       ((and meta-left-comment-regexp
             (looking-at meta-left-comment-regexp))
        0)
!       ;; Comments to the right margin.
       ((and meta-right-comment-regexp
             (looking-at meta-right-comment-regexp))
        comment-column)
--- 605,620 ----
  
  (defun meta-indent-calculate ()
    "Return the indentation of current line of Metafont or MetaPost source."
+   ;; Indentation within strings is not considered as Meta* don't allow multi
+   ;; line strings.
    (save-excursion
      (back-to-indentation)
      (cond
!      ;; Comments to the left margin.
       ((and meta-left-comment-regexp
             (looking-at meta-left-comment-regexp))
        0)
!      ;; Comments to the right margin.
       ((and meta-right-comment-regexp
             (looking-at meta-right-comment-regexp))
        comment-column)
***************
*** 620,661 ****
       ((and meta-ignore-comment-regexp
             (looking-at meta-ignore-comment-regexp))
        (current-indentation))
       ;; Backindent at end of environments.
!      ((looking-at
         (concat "\\<" meta-end-environment-regexp "\\>"))
!       (- (meta-indent-calculate-last) meta-indent-level))
       ;; Backindent at keywords within environments.
!      ((looking-at
         (concat "\\<" meta-within-environment-regexp "\\>"))
!       (- (meta-indent-calculate-last) meta-indent-level))
!      (t (meta-indent-calculate-last)))))
  
! (defun meta-indent-calculate-last ()
!   "Return the indentation of previous line of Metafont or MetaPost source."
!   (save-restriction
!     (widen)
      (skip-chars-backward "\n\t ")
!     (move-to-column (current-indentation))
!     ;; Ignore comments.
!     (while (and (looking-at comment-start) (not (bobp)))
!       (skip-chars-backward "\n\t ")
!       (if (not (bobp))
!           (move-to-column (current-indentation))))
!     (cond
!      ((bobp) 0)
!      (t (+ (current-indentation)
!            (meta-indent-level-count)
!            (cond
!             ;; Compensate for backindent at end of environments.
!             ((looking-at
!               (concat "\\<"meta-end-environment-regexp "\\>"))
!              meta-indent-level)
!             ;; Compensate for backindent within environments.
!             ((looking-at
!               (concat "\\<" meta-within-environment-regexp "\\>"))
!              meta-indent-level)
!             (t 0)))))
!     ))
  
  (defun meta-indent-level-count ()
    "Count indentation change for begin-end commands in the current line."
--- 622,734 ----
       ((and meta-ignore-comment-regexp
             (looking-at meta-ignore-comment-regexp))
        (current-indentation))
+      ;; Beginning of buffer.
+      ((eq (point-at-bol) (point-min))
+       0)
       ;; Backindent at end of environments.
!      ((meta-indent-looking-at-code
         (concat "\\<" meta-end-environment-regexp "\\>"))
!       (- (meta-indent-current-indentation) meta-indent-level))
       ;; Backindent at keywords within environments.
!      ((meta-indent-looking-at-code
         (concat "\\<" meta-within-environment-regexp "\\>"))
!       (- (meta-indent-current-indentation) meta-indent-level))
!      (t (meta-indent-current-indentation)))))
  
! (defun meta-indent-in-string-p ()
!   "Tell if the point is in a string."
!   (or (nth 3 (syntax-ppss))
!       (eq (get-text-property (point) 'face) font-lock-string-face)))
! 
! (defun meta-indent-looking-at-code (regexp)
!   "Same as `looking-at' but checks that the point is not in a string."
!   (unless (meta-indent-in-string-p)
!     (looking-at regexp)))
! 
! (defun meta-indent-previous-line ()
!   "Go to the previous line of code, skipping comments."
!   (skip-chars-backward "\n\t ")
!   (move-to-column (current-indentation))
!   ;; Ignore comments.
!   (while (and (looking-at comment-start) (not (bobp)))
      (skip-chars-backward "\n\t ")
!     (if (not (bobp))
!       (move-to-column (current-indentation)))))
! 
! (defun meta-indent-unfinished-line ()
!   "Tell if the current line of code ends with an unfinished expression."
!   (save-excursion
!     (end-of-line)
!     ;; Skip backward the comments.
!     (while (search-backward comment-start (point-at-bol) t))
!     ;; Search for the end of the previous expression.
!     (if (search-backward ";" (point-at-bol) t)
!       (progn (while (and (meta-indent-in-string-p)
!                          (search-backward ";" (point-at-bol) t)))
!              (if (= (char-after) ?\;)
!                  (forward-char)
!                (beginning-of-line)))
!       (beginning-of-line))
!     ;; See if the last statement of the line is environment-related,
!     ;; or exists at all.
!     (if (meta-indent-looking-at-code
!        (concat "[ \t]*\\($\\|" (regexp-quote comment-start)
!                "\\|\\<" meta-end-environment-regexp "\\>"
!                "\\|\\<" meta-begin-environment-regexp "\\>"
!                "\\|\\<" meta-within-environment-regexp "\\>\\)"))
!       nil
!       t)))
! 
! (defun meta-indent-current-indentation ()
!   "Return the indentation wanted for the current line of code."
!   (+ (meta-indent-current-nesting)
!      (if (save-excursion
!          (back-to-indentation)
!          (and (not (looking-at (concat "\\<" meta-end-environment-regexp "\\>"
!                                        "\\|\\<" 
meta-within-environment-regexp "\\>")))
!               (progn (meta-indent-previous-line)
!                      (meta-indent-unfinished-line))))
!        meta-indent-level
!        0)))
! 
! (defun meta-indent-current-nesting ()
!   "Return the indentation according to the nearest environment keyword."
!   (save-excursion
!     (save-restriction
!       (widen)
!       (back-to-indentation)
!       (let ((to-add 0))
!       ;; If we found some environment marker backward...
!       (if (catch 'found
!             (while (re-search-backward
!                     (concat "(\\|)\\|\\<" meta-end-environment-regexp "\\>"
!                             "\\|\\<" meta-begin-environment-regexp "\\>"
!                             "\\|\\<" meta-within-environment-regexp "\\>")
!                     nil t)
!               ;; If we aren't in a string or in a comment, we've found 
something.
!               (unless (or (meta-indent-in-string-p)
!                           (nth 4 (syntax-ppss)))
!                 (cond ((= (char-after) ?\()
!                        (setq to-add (+ to-add meta-indent-level)))
!                       ((= (char-after) ?\))
!                        (setq to-add (- to-add meta-indent-level)))
!                       (t (throw 'found t))))))
!           (progn
!             ;; ... then use it to compute the current indentation.
!             (back-to-indentation)
!             (+ to-add (current-indentation) (meta-indent-level-count)
!                ;; Compensate for backindent of end and within keywords.
!                (if (meta-indent-looking-at-code
!                     (concat "\\<" meta-end-environment-regexp "\\>\\|"
!                             "\\<" meta-within-environment-regexp "\\>"))
!                    meta-indent-level
!                  ;; Compensate for unfinished line.
!                  (if (save-excursion
!                        (meta-indent-previous-line)
!                        (meta-indent-unfinished-line))
!                      (- meta-indent-level)
!                    0))))
!         0)))))
  
  (defun meta-indent-level-count ()
    "Count indentation change for begin-end commands in the current line."
***************
*** 671,688 ****
              (goto-char (match-beginning 0))
              (cond
               ;; Count number of begin-end keywords within line.
!              ((looking-at
                 (concat "\\<" meta-begin-environment-regexp "\\>"))
                (setq count (+ count meta-indent-level)))
!              ((looking-at
                 (concat "\\<" meta-end-environment-regexp "\\>"))
!               (setq count (- count meta-indent-level)))
!              ;; Count number of open-close parentheses within line.
!              ((looking-at "(")
!               (setq count (+ count meta-indent-level)))
!              ((looking-at ")")
!               (setq count (- count meta-indent-level)))
!              )))
          count))))
  
  
--- 744,755 ----
              (goto-char (match-beginning 0))
              (cond
               ;; Count number of begin-end keywords within line.
!              ((meta-indent-looking-at-code
                 (concat "\\<" meta-begin-environment-regexp "\\>"))
                (setq count (+ count meta-indent-level)))
!              ((meta-indent-looking-at-code
                 (concat "\\<" meta-end-environment-regexp "\\>"))
!               (setq count (- count meta-indent-level))))))
          count))))
  
  
Index: lisp/ChangeLog
===================================================================
RCS file: /sources/emacs/emacs/lisp/ChangeLog,v
retrieving revision 1.11534
diff -C 0 -r1.11534 ChangeLog
*** lisp/ChangeLog      8 Aug 2007 16:38:31 -0000       1.11534
--- lisp/ChangeLog      9 Aug 2007 13:13:46 -0000
***************
*** 0 ****
--- 1,18 ----
+ 2007-08-09  Michaël Cadilhac  <address@hidden>
+ 
+       * progmodes/meta-mode.el (meta-indent-calculate-last): Remove.
+       (meta-indent-current-nesting): Use a computation of the nesting
+       instead.
+       (meta-indent-current-indentation): Indentation is given according
+       to nesting and if the previous line was finished or not.
+       (meta-indent-unfinished-line): Tell if the current line ends with
+       a finished expression.
+       (meta-indent-looking-at-code): Like `looking-at', but checks if
+       the point is a string before.
+       (meta-indent-level-count): Use it.  Don't count parenthesis as it's
+       done in the nesting function.
+       (meta-indent-in-string-p): Tell if the current point is in a
+       string.
+       (meta-indent-calculate): Treat b-o-b as a special case.  Use the
+       previous functions
+ 
-- 
 |   Michaël `Micha' Cadilhac       |    The second-degree,                  |
 |   http://michael.cadilhac.name   |       is kind of                       |
 |   JID/MSN:                       |   the semantic back slang.             |
 `----  address@hidden  |                                   -  --'

Attachment: pgpoiyuOMtBtj.pgp
Description: PGP signature


reply via email to

[Prev in Thread] Current Thread [Next in Thread]