emacs-diffs
[Top][All Lists]
Advanced

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

[Emacs-diffs] Changes to emacs/lisp/progmodes/idlwave.el


From: John-David T. Smith
Subject: [Emacs-diffs] Changes to emacs/lisp/progmodes/idlwave.el
Date: Thu, 12 Sep 2002 12:59:24 -0400

Index: emacs/lisp/progmodes/idlwave.el
diff -c emacs/lisp/progmodes/idlwave.el:3.20 
emacs/lisp/progmodes/idlwave.el:3.21
*** emacs/lisp/progmodes/idlwave.el:3.20        Fri Sep  6 03:16:01 2002
--- emacs/lisp/progmodes/idlwave.el     Thu Sep 12 12:59:24 2002
***************
*** 1,11 ****
! ;;; idlwave.el --- IDL and WAVE CL editing mode for GNU Emacs
  ;; Copyright (c) 1999, 2000, 2001,2002 Free Software Foundation
  
  ;; Author: Carsten Dominik <address@hidden>
  ;;         Chris Chase <address@hidden>
  ;; Maintainer: J.D. Smith <address@hidden>
! ;; Version: 4.14
! ;; Date: $Date: 2002/09/06 07:16:01 $
  ;; Keywords: languages
  
  ;; This file is part of GNU Emacs.
--- 1,11 ----
! ;;; idlwave.el --- IDL editing mode for GNU Emacs
  ;; Copyright (c) 1999, 2000, 2001,2002 Free Software Foundation
  
  ;; Author: Carsten Dominik <address@hidden>
  ;;         Chris Chase <address@hidden>
  ;; Maintainer: J.D. Smith <address@hidden>
! ;; Version: 4.15
! ;; Date: $Date: 2002/09/12 16:59:24 $
  ;; Keywords: languages
  
  ;; This file is part of GNU Emacs.
***************
*** 57,63 ****
  ;; SOURCE
  ;; ======
  ;;
! ;; The newest version of this file is available from the maintainers
  ;; Webpage.
  ;;
  ;;   http://idlwave.org
--- 57,63 ----
  ;; SOURCE
  ;; ======
  ;;
! ;; The newest version of this file is available from the maintainer's
  ;; Webpage.
  ;;
  ;;   http://idlwave.org
***************
*** 84,109 ****
  ;;    Simon Marshall <address@hidden>
  ;;    Laurent Mugnier <address@hidden>
  ;;    Lubos Pochman <address@hidden>
  ;;    Patrick M. Ryan <address@hidden>
  ;;    Marty Ryba <address@hidden>
  ;;    Phil Williams <address@hidden>
- ;;    J.D. Smith <address@hidden>
  ;;    Phil Sterne <address@hidden>
  ;;
  ;; CUSTOMIZATION:
  ;; =============
  ;;
! ;; IDLWAVE has customize support - so if you want to learn about the
! ;;  variables which control the behavior of the mode, use
  ;; `M-x idlwave-customize'.
  ;;
  ;; You can set your own preferred values with Customize, or with Lisp
  ;; code in .emacs.  For an example of what to put into .emacs, check
! ;; the TexInfo documentation.
  ;;
  ;; KNOWN PROBLEMS:
  ;; ==============
  ;;
  ;;   Moving the point backwards in conjunction with abbrev expansion
  ;;   does not work as I would like it, but this is a problem with
  ;;   emacs abbrev expansion done by the self-insert-command.  It ends
--- 84,116 ----
  ;;    Simon Marshall <address@hidden>
  ;;    Laurent Mugnier <address@hidden>
  ;;    Lubos Pochman <address@hidden>
+ ;;    Bob Portmann <address@hidden>
  ;;    Patrick M. Ryan <address@hidden>
  ;;    Marty Ryba <address@hidden>
  ;;    Phil Williams <address@hidden>
  ;;    Phil Sterne <address@hidden>
  ;;
  ;; CUSTOMIZATION:
  ;; =============
  ;;
! ;; IDLWAVE has extensive customize support - so if you want to learn
! ;; about the variables which control the behavior of the mode, use
  ;; `M-x idlwave-customize'.
  ;;
  ;; You can set your own preferred values with Customize, or with Lisp
  ;; code in .emacs.  For an example of what to put into .emacs, check
! ;; the TexInfo documentation or see a complete .emacs at
! ;; http://idlwave.org.
  ;;
  ;; KNOWN PROBLEMS:
  ;; ==============
  ;;
+ ;;   IDLWAVE support for the IDL-derived PV-WAVE CL language of Visual
+ ;;   Numerics, Inc. is growing less and less complete as the two
+ ;;   languages grow increasingly apart.  The mode probably shouldn't
+ ;;   even have "WAVE" in it's title, but it's catchy, and required to
+ ;;   avoid conflict with the CORBA idl.el mode.  Caveat WAVEor.
+ ;;
  ;;   Moving the point backwards in conjunction with abbrev expansion
  ;;   does not work as I would like it, but this is a problem with
  ;;   emacs abbrev expansion done by the self-insert-command.  It ends
***************
*** 120,134 ****
  ;;   limited to comments only and occurs only when a comment
  ;;   paragraph is filled via `idlwave-fill-paragraph'.
  ;;
- ;;   "&" is ignored when parsing statements.
  ;;   Avoid muti-statement lines (using "&") on block begin and end
  ;;   lines.  Multi-statement lines can mess up the formatting, for
  ;;   example, multiple end statements on a line: endif & endif.
  ;;   Using "&" outside of block begin/end lines should be okay.
  ;;
! ;;   It is possible that the parser which decides what to complete has
! ;;   problems with pointer dereferencing statements.  I don't use
! ;;   pointers often enough to find out - please report any problems.
  ;;
  ;;   When forcing completion of method keywords, the initial
  ;;   query for a method has multiple entries for some methods.  Would
--- 127,141 ----
  ;;   limited to comments only and occurs only when a comment
  ;;   paragraph is filled via `idlwave-fill-paragraph'.
  ;;
  ;;   Avoid muti-statement lines (using "&") on block begin and end
  ;;   lines.  Multi-statement lines can mess up the formatting, for
  ;;   example, multiple end statements on a line: endif & endif.
  ;;   Using "&" outside of block begin/end lines should be okay.
  ;;
! ;;   Determining the expression at point for printing and other
! ;;   examination commands is somewhat rough: currently only fairly
! ;;   simple entities are found.  You can always drag-select or examine
! ;;   a region.
  ;;
  ;;   When forcing completion of method keywords, the initial
  ;;   query for a method has multiple entries for some methods.  Would
***************
*** 653,669 ****
  When IDLWAVE tries to complete object-oriented methods, it usually
  cannot determine the class of a given object from context.  In order
  to provide the user with a correct list of methods or keywords, it
! needs have to determine the appropriate class.  IDLWAVE has two ways
! to deal with this problem.
! 
! 1. One possibility is to combine the items of all available classes
!    which contain this method for the purpose of completion.  So when
!    completing a method, all methods of all known classes are
!    available, and when completing a keyword, all keywords allowed for
!    this method in any class are shown.  This behavior is very much
!    like normal completion and is therefore the default.  It works much
!    better than one might think - only for the INIT, GETPROPERTY and
!    SETPROPERTY the keyword lists become uncomfortably long.  See also
     `idlwave-completion-show-classes'.
  
  2. The second possibility is to ask the user on each occasion.  To
--- 660,677 ----
  When IDLWAVE tries to complete object-oriented methods, it usually
  cannot determine the class of a given object from context.  In order
  to provide the user with a correct list of methods or keywords, it
! needs to determine the appropriate class.  IDLWAVE has two ways of
! doing this (well, three ways if you count the shell... see
! `idlwave-shell-query-for-class'):
! 
! 1. Combine the items of all available classes which contain this
!    method for the purpose of completion.  So when completing a method,
!    all methods of all known classes are available, and when completing
!    a keyword, all keywords allowed for this method in any class are
!    shown.  This behavior is very much like normal completion and is
!    therefore the default.  It works much better than one might think -
!    only for the INIT, GETPROPERTY and SETPROPERTY the keyword lists
!    become uncomfortably long.  See also
     `idlwave-completion-show-classes'.
  
  2. The second possibility is to ask the user on each occasion.  To
***************
*** 1156,1193 ****
  (defconst idlwave-font-lock-keywords-3 nil
    "Gaudy level highlighting for IDLWAVE mode.")
  
  (let* ((oldp (or (string-match "Lucid" emacs-version)
                 (not (boundp 'emacs-minor-version))
                 (and (<= emacs-major-version 19) 
                      (<= emacs-minor-version 29))))
! 
!        ;; The following are the reserved words in IDL.  Maybe we should
!        ;; highlight some more stuff as well?       
!        (idl-keywords
!       ;; To update this regexp, update the list of keywords and 
!       ;; evaluate the form.
! ;     (insert 
! ;      (prin1-to-string
! ;       (concat 
! ;        "\\<\\("
! ;        (regexp-opt 
! ;         '("and" "or" "xor" "not"
! ;           "eq" "ge" "gt" "le" "lt" "ne" 
! ;           "for" "do" "endfor"
! ;           "if" "then" "endif" "else" "endelse" 
! ;           "case" "of" "endcase"
! ;           "switch" "break" "continue" "endswitch"
! ;           "begin" "end"
! ;           "repeat" "until" "endrep"
! ;           "while" "endwhile" 
! ;           "goto" "return"
! ;           "inherits" "mod"
! ;           "compile_opt" "forward_function"
! ;           "on_error" "on_ioerror"))  ; on_error is not officially reserved
! ;        "\\)\\>")))
! 
!       
"\\<\\(and\\|b\\(egin\\|reak\\)\\|c\\(ase\\|o\\(mpile_opt\\|ntinue\\)\\)\\|do\\|e\\(lse\\|nd\\(case\\|else\\|for\\|if\\|rep\\|switch\\|while\\)?\\|q\\)\\|for\\(ward_function\\)?\\|g\\(oto\\|[et]\\)\\|i\\(f\\|nherits\\)\\|l[et]\\|mod\\|n\\(e\\|ot\\)\\|o\\(n_\\(error\\|ioerror\\)\\|[fr]\\)\\|re\\(peat\\|turn\\)\\|switch\\|then\\|until\\|while\\|xor\\)\\>")
! 
         ;; Procedure declarations.  Fontify keyword plus procedure name.
         ;; Function  declarations.  Fontify keyword plus function  name.
         (pros-and-functions
--- 1164,1202 ----
  (defconst idlwave-font-lock-keywords-3 nil
    "Gaudy level highlighting for IDLWAVE mode.")
  
+ ;; The following are the reserved words in IDL.  Maybe we should
+ ;; highlight some more stuff as well?       
+ ;; Procedure declarations.  Fontify keyword plus procedure name.
+ (defvar idlwave-idl-keywords
+   ;; To update this regexp, update the list of keywords and 
+   ;; evaluate the form.
+   ;;  (insert 
+   ;;   (prin1-to-string
+   ;;    (concat 
+   ;;     "\\<\\("
+   ;;     (regexp-opt 
+   ;;      '("and" "or" "xor" "not"
+   ;;        "eq" "ge" "gt" "le" "lt" "ne" 
+   ;;        "for" "do" "endfor"
+   ;;        "if" "then" "endif" "else" "endelse" 
+   ;;        "case" "of" "endcase"
+   ;;        "switch" "break" "continue" "endswitch"
+   ;;        "begin" "end"
+   ;;        "repeat" "until" "endrep"
+   ;;        "while" "endwhile" 
+   ;;        "goto" "return"
+   ;;        "inherits" "mod"
+   ;;        "compile_opt" "forward_function"
+   ;;        "on_error" "on_ioerror"))  ; on_error is not officially reserved
+   ;;     "\\)\\>")))
+   
"\\<\\(and\\|b\\(egin\\|reak\\)\\|c\\(ase\\|o\\(mpile_opt\\|ntinue\\)\\)\\|do\\|e\\(lse\\|nd\\(case\\|else\\|for\\|if\\|rep\\|switch\\|while\\)?\\|q\\)\\|for\\(ward_function\\)?\\|g\\(oto\\|[et]\\)\\|i\\(f\\|nherits\\)\\|l[et]\\|mod\\|n\\(e\\|ot\\)\\|o\\(n_\\(error\\|ioerror\\)\\|[fr]\\)\\|re\\(peat\\|turn\\)\\|switch\\|then\\|until\\|while\\|xor\\)\\>")
+ 
  (let* ((oldp (or (string-match "Lucid" emacs-version)
                 (not (boundp 'emacs-minor-version))
                 (and (<= emacs-major-version 19) 
                      (<= emacs-minor-version 29))))
!        
!        (idl-keywords idlwave-idl-keywords)
         ;; Procedure declarations.  Fontify keyword plus procedure name.
         ;; Function  declarations.  Fontify keyword plus function  name.
         (pros-and-functions
***************
*** 1268,1274 ****
    ;; The following lines are just a dummy to make the compiler shut up
    ;; about variables bound but not used.
    (setq oldp oldp
-       idl-keywords idl-keywords
        pros-and-functions pros-and-functions
        common-blocks common-blocks
        batch-files batch-files
--- 1277,1282 ----
***************
*** 1294,1300 ****
    (setq idlwave-font-lock-keywords-3 
        (list pros-and-functions
              batch-files
!             idl-keywords
              label goto
              structtag
              structname
--- 1302,1308 ----
    (setq idlwave-font-lock-keywords-3 
        (list pros-and-functions
              batch-files
!             idlwave-idl-keywords
              label goto
              structtag
              structname
***************
*** 1437,1443 ****
    "Character which is inserted as a last character on previous line by
     \\[idlwave-split-line] to begin a continuation line.  Normally $.")
  
! (defconst idlwave-mode-version " 4.14")
  
  (defmacro idlwave-keyword-abbrev (&rest args)
    "Creates a function for abbrev hooks to call `idlwave-check-abbrev' with 
args."
--- 1445,1451 ----
    "Character which is inserted as a last character on previous line by
     \\[idlwave-split-line] to begin a continuation line.  Normally $.")
  
! (defconst idlwave-mode-version " 4.15")
  
  (defmacro idlwave-keyword-abbrev (&rest args)
    "Creates a function for abbrev hooks to call `idlwave-check-abbrev' with 
args."
***************
*** 1494,1520 ****
  
  (modify-syntax-entry ?$   "w"  idlwave-find-symbol-syntax-table)
  (modify-syntax-entry ?_   "w"  idlwave-find-symbol-syntax-table)
- 
- (defmacro idlwave-with-special-syntax (&rest body)
-   "Execute BODY with a different systax table."
-   `(let ((saved-syntax (syntax-table)))
-      (unwind-protect
-        (progn
-          (set-syntax-table idlwave-find-symbol-syntax-table)
-          ,@body)
-        (set-syntax-table saved-syntax))))
- 
- (defvar idlwave-print-symbol-syntax-table
-   (copy-syntax-table idlwave-mode-syntax-table)
-   "Syntax table that treats symbol characters as word characters.")
- 
- (modify-syntax-entry ?$   "w"  idlwave-find-symbol-syntax-table)
- (modify-syntax-entry ?_   "w"  idlwave-find-symbol-syntax-table)
  (modify-syntax-entry ?!   "w"  idlwave-find-symbol-syntax-table)
  (modify-syntax-entry ?.   "w"  idlwave-find-symbol-syntax-table)
  
! (defmacro idlwave-with-special-syntax1 (&rest body)
!   "Execute BODY with a different systax table."
    `(let ((saved-syntax (syntax-table)))
       (unwind-protect
         (progn
--- 1502,1512 ----
  
  (modify-syntax-entry ?$   "w"  idlwave-find-symbol-syntax-table)
  (modify-syntax-entry ?_   "w"  idlwave-find-symbol-syntax-table)
  (modify-syntax-entry ?!   "w"  idlwave-find-symbol-syntax-table)
  (modify-syntax-entry ?.   "w"  idlwave-find-symbol-syntax-table)
  
! (defmacro idlwave-with-special-syntax (&rest body)
!   "Execute BODY with a different syntax table."
    `(let ((saved-syntax (syntax-table)))
       (unwind-protect
         (progn
***************
*** 1522,1527 ****
--- 1514,1528 ----
           ,@body)
         (set-syntax-table saved-syntax))))
  
+ ;(defmacro idlwave-with-special-syntax1 (&rest body)
+ ;  "Execute BODY with a different syntax table."
+ ;  `(let ((saved-syntax (syntax-table)))
+ ;     (unwind-protect
+ ;       (progn
+ ;         (set-syntax-table idlwave-find-symbol-syntax-table)
+ ;         ,@body)
+ ;     (set-syntax-table saved-syntax))))
+ 
  (defun idlwave-action-and-binding (key cmd &optional select)
    "KEY and CMD are made into a key binding and an indent action.
  KEY is a string - same as for the `define-key' function.  CMD is a
***************
*** 1576,1581 ****
--- 1577,1583 ----
  ;(define-key idlwave-mode-map "\C-c\C- " 'idlwave-hard-tab)
  (define-key idlwave-mode-map "'"        'idlwave-show-matching-quote)
  (define-key idlwave-mode-map "\""       'idlwave-show-matching-quote)
+ (define-key idlwave-mode-map "\C-g"     'idlwave-keyboard-quit)
  (define-key idlwave-mode-map "\C-c;"    'idlwave-toggle-comment-region)
  (define-key idlwave-mode-map "\C-\M-a"  'idlwave-beginning-of-subprogram)
  (define-key idlwave-mode-map "\C-\M-e"  'idlwave-end-of-subprogram)
***************
*** 1593,1599 ****
  (define-key idlwave-mode-map "\C-c\C-n" 'idlwave-next-statement)
  ;; (define-key idlwave-mode-map "\r"       'idlwave-newline)
  ;; (define-key idlwave-mode-map "\t"       'idlwave-indent-line)
! (define-key idlwave-mode-map (kbd "S-<iso-lefttab>") 
'idlwave-indent-statement)
  (define-key idlwave-mode-map "\C-c\C-a" 'idlwave-auto-fill-mode)
  (define-key idlwave-mode-map "\M-q"     'idlwave-fill-paragraph)
  (define-key idlwave-mode-map "\M-s"     'idlwave-edit-in-idlde)
--- 1595,1601 ----
  (define-key idlwave-mode-map "\C-c\C-n" 'idlwave-next-statement)
  ;; (define-key idlwave-mode-map "\r"       'idlwave-newline)
  ;; (define-key idlwave-mode-map "\t"       'idlwave-indent-line)
! (define-key idlwave-mode-map [(shift tab)] 'idlwave-indent-statement)
  (define-key idlwave-mode-map "\C-c\C-a" 'idlwave-auto-fill-mode)
  (define-key idlwave-mode-map "\M-q"     'idlwave-fill-paragraph)
  (define-key idlwave-mode-map "\M-s"     'idlwave-edit-in-idlde)
***************
*** 1637,1642 ****
--- 1639,1645 ----
  (define-key idlwave-mode-map "\C-c\C-v"   'idlwave-find-module)
  (define-key idlwave-mode-map "\C-c?"      'idlwave-routine-info)
  (define-key idlwave-mode-map "\M-?"       'idlwave-context-help)
+ (define-key idlwave-mode-map [(control meta ?\?)] 'idlwave-online-help)
  (define-key idlwave-mode-map [(meta tab)] 'idlwave-complete)
  (define-key idlwave-mode-map "\C-c\C-i"   'idlwave-update-routine-info)
  (define-key idlwave-mode-map "\C-c="      'idlwave-resolve)
***************
*** 1965,1971 ****
         "[ \t\f]*$\\|[ \t]*;+[ \t]*$\\|;+[+=-_*]+$")
    (set (make-local-variable 'paragraph-start) "[ \t\f]\\|[ \t]*;+[ \t]")
    (set (make-local-variable 'paragraph-ignore-fill-prefix) nil)
!   (set (make-local-variable 'parse-sexp-ignore-comments) nil)
    
    ;; Set tag table list to use IDLTAGS as file name.
    (if (boundp 'tag-table-alist)
--- 1968,1974 ----
         "[ \t\f]*$\\|[ \t]*;+[ \t]*$\\|;+[+=-_*]+$")
    (set (make-local-variable 'paragraph-start) "[ \t\f]\\|[ \t]*;+[ \t]")
    (set (make-local-variable 'paragraph-ignore-fill-prefix) nil)
!   (set (make-local-variable 'parse-sexp-ignore-comments) t)
    
    ;; Set tag table list to use IDLTAGS as file name.
    (if (boundp 'tag-table-alist)
***************
*** 2134,2151 ****
    "Finds the start of current block and blinks to it for a second.
  Also checks if the correct end statement has been used."
    ;; All end statements are reserved words
!   (let* ((pos (point))
!        end end1)
      (when (and (idlwave-check-abbrev 0 t)
               idlwave-show-block)
        (save-excursion
        ;; Move inside current block
!       (setq end (buffer-substring 
!                  (save-excursion (skip-chars-backward "a-zA-Z")
!                                  (point))
!                  (point)))
!       (idlwave-beginning-of-statement)
        (idlwave-block-jump-out -1 'nomark)
        (when (setq end1 (cdr (idlwave-block-master)))
          (cond
           ((null end1)) ; no-operation
--- 2137,2169 ----
    "Finds the start of current block and blinks to it for a second.
  Also checks if the correct end statement has been used."
    ;; All end statements are reserved words
!   ;; Re-indent end line
!   (insert-char ?\ 1) ;; So indent, etc. work well
!   (backward-char 1)
!   (let* ((pos (point-marker))
!        (last-abbrev-marker (copy-marker last-abbrev-location))
!        (eol-pos (save-excursion (end-of-line) (point)))
!        begin-pos end-pos end end1 )
!     (if idlwave-reindent-end  (idlwave-indent-line))
!     
      (when (and (idlwave-check-abbrev 0 t)
               idlwave-show-block)
        (save-excursion
        ;; Move inside current block
!       (goto-char last-abbrev-marker)
        (idlwave-block-jump-out -1 'nomark)
+       (setq begin-pos (point))
+       (idlwave-block-jump-out 1 'nomark)
+       (setq end-pos (point))
+       (if (> end-pos eol-pos)
+           (setq end-pos pos))
+       (goto-char end-pos)
+       (setq end (buffer-substring 
+                  (progn
+                    (skip-chars-backward "a-zA-Z")
+                    (point))
+                  end-pos))
+       (goto-char begin-pos)
        (when (setq end1 (cdr (idlwave-block-master)))
          (cond
           ((null end1)) ; no-operation
***************
*** 2165,2173 ****
            (message "Warning: Shouldn't this be \"%s\" instead of \"%s\"?" 
                     end1 end)
            (sit-for 1)))))))
!   ;; Re-indent end line
!   (if idlwave-reindent-end
!       (idlwave-indent-line)))
  
  (defun idlwave-block-master ()
    (let ((case-fold-search t))
--- 2183,2189 ----
            (message "Warning: Shouldn't this be \"%s\" instead of \"%s\"?" 
                     end1 end)
            (sit-for 1)))))))
!   (delete-char 1))
  
  (defun idlwave-block-master ()
    (let ((case-fold-search t))
***************
*** 2588,2593 ****
--- 2604,2617 ----
                         (looking-at "^@")))))
      last-statement))
  
+ (defun idlwave-skip-multi-commands (&optional lim)
+   "Skip past multiple commands on a line (with `&')."
+   (let ((save-point (point)))
+     (when (re-search-forward ".*&" lim t)
+       (goto-char (match-end 0))
+       (if (idlwave-in-quote) (goto-char save-point)))
+     (point)))
+ 
  (defun idlwave-skip-label-or-case ()
    "Skip label or case statement element.
  Returns position after label.
***************
*** 2627,2632 ****
--- 2651,2657 ----
          st nst last)
      (idlwave-beginning-of-statement)
      (idlwave-skip-label-or-case)
+     (idlwave-skip-multi-commands orig)
      (setq last (point))
      ;; Continue looking for substatements until we are past orig
      (while (and (<= (point) orig) (not (eobp)))
***************
*** 2656,2662 ****
  statement."
    (save-excursion
      ;; Skip whitespace within a statement which is spaces, tabs, continuations
!     (while (looking-at "[ \t]*\\<\\$")
        (forward-line 1))
      (skip-chars-forward " \t")
      (let ((st idlwave-statement-match)
--- 2681,2688 ----
  statement."
    (save-excursion
      ;; Skip whitespace within a statement which is spaces, tabs, continuations
!     ;; and possibly comments
!     (while (looking-at "[ \t]*\\$")
        (forward-line 1))
      (skip-chars-forward " \t")
      (let ((st idlwave-statement-match)
***************
*** 2757,2769 ****
            ;; indent the line
            (idlwave-indent-left-margin (idlwave-calculate-indent)))
          ;; Adjust parallel comment
!         (end-of-line)
!         (if (idlwave-in-comment)
!             (indent-for-comment))))
      (goto-char mloc)
      ;; Get rid of marker
!     (set-marker mloc nil)
!     ))
  
  (defun idlwave-do-action (action)
    "Perform an action repeatedly on a line.
--- 2783,2798 ----
            ;; indent the line
            (idlwave-indent-left-margin (idlwave-calculate-indent)))
          ;; Adjust parallel comment
!       (end-of-line)
!       (if (idlwave-in-comment)
!           ;; Emacs 21 is too smart with fill-column on comment indent
!           (let ((fill-column (if (fboundp 'comment-indent-new-line)
!                                  (1- (frame-width))
!                                fill-column)))
!             (indent-for-comment)))))
      (goto-char mloc)
      ;; Get rid of marker
!     (set-marker mloc nil)))
  
  (defun idlwave-do-action (action)
    "Perform an action repeatedly on a line.
***************
*** 2895,2901 ****
             (case-fold-search t)
             (end-reg (progn (beginning-of-line) (point)))
             (close-exp (progn (skip-chars-forward " \t") (looking-at "\\s)")))
!            (beg-reg (progn (idlwave-previous-statement) (point)))
           (cur-indent (idlwave-current-indent))
           (else-cont (and (goto-char end-reg) (looking-at "[ \t]*else")))
           (basic-indent           ;; The basic, non-fancy indent
--- 2924,2935 ----
             (case-fold-search t)
             (end-reg (progn (beginning-of-line) (point)))
             (close-exp (progn (skip-chars-forward " \t") (looking-at "\\s)")))
! ;           (beg-reg (progn (idlwave-previous-statement) (point)))
!            (beg-reg (progn ;; Use substatement indent unless it's this line
!                     (idlwave-start-of-substatement 'pre) 
!                     (if (eq (line-beginning-position) end-reg)
!                         (idlwave-previous-statement))
!                     (point)))
           (cur-indent (idlwave-current-indent))
           (else-cont (and (goto-char end-reg) (looking-at "[ \t]*else")))
           (basic-indent           ;; The basic, non-fancy indent
***************
*** 2908,2914 ****
              (cond
               ;; A continued Procedure call or definition
               ((progn
!                 (idlwave-look-at "\\(pro\\|function\\)")
                  (looking-at "[ \t]*\\([a-zA-Z0-9$_]+[ \t]*->[ 
\t]*\\)?[a-zA-Z][:a-zA-Z0-9$_]*[ \t]*\\(,\\)[ \t]*"))
                (goto-char (match-end 0))
                ;; Comment only, or blank line with "$"?  Align with ,
--- 2942,2948 ----
              (cond
               ;; A continued Procedure call or definition
               ((progn
!                 (idlwave-look-at "^[ \t]*\\(pro\\|function\\)") ;skip over
                  (looking-at "[ \t]*\\([a-zA-Z0-9$_]+[ \t]*->[ 
\t]*\\)?[a-zA-Z][:a-zA-Z0-9$_]*[ \t]*\\(,\\)[ \t]*"))
                (goto-char (match-end 0))
                ;; Comment only, or blank line with "$"?  Align with ,
***************
*** 2917,2923 ****
                (current-column))
  
               ;; Continued assignment (with =), 
!              ((looking-at "[ \t]*[a-zA-Z0-9$_]+[ \t]*\\(=\\)[ \t]*")
                (goto-char (match-end 0))
                ;; Comment only?  Align with =
                (if (save-match-data (looking-at "[ \t$]*\\(;.*\\)?$"))
--- 2951,2957 ----
                (current-column))
  
               ;; Continued assignment (with =), 
!              ((looking-at "[ \t]*[][().a-zA-Z0-9$_]+[ \t]*\\(=\\)[ \t]*")
                (goto-char (match-end 0))
                ;; Comment only?  Align with =
                (if (save-match-data (looking-at "[ \t$]*\\(;.*\\)?$"))
***************
*** 3574,3579 ****
--- 3608,3625 ----
        ;; return string beginning position or nil
        (if (> start bq) bq))))
  
+ (defun idlwave-is-pointer-dereference (&optional limit)
+   "Determines if the character after point is a pointer dereference *."
+   (let ((pos (point)))
+     (and
+      (eq (char-after) ?\*)
+      (not (idlwave-in-quote))
+      (save-excursion
+        (forward-char)
+        (re-search-backward (concat "\\(" idlwave-idl-keywords 
+                                  "\\|[[(*+-/=,^><]\\)\\s-*\\*") limit t)))))
+ 
+ 
  ;; Statement templates
  
  ;; Replace these with a general template function, something like
***************
*** 3951,3957 ****
  ;; "sinterned" strings.  The only exception is that the functions
  ;; which scan whole buffers for routine information do not intern the
  ;; grabbed strings.  This is only done afterwards.  Therefore in these 
! ;; functions it is *not* save to assume the strings can be compared
  ;; with `eq' and be fed into the routine assq functions.
  
  ;; Here we define the hashing functions.
--- 3997,4003 ----
  ;; "sinterned" strings.  The only exception is that the functions
  ;; which scan whole buffers for routine information do not intern the
  ;; grabbed strings.  This is only done afterwards.  Therefore in these 
! ;; functions it is *not* safe to assume the strings can be compared
  ;; with `eq' and be fed into the routine assq functions.
  
  ;; Here we define the hashing functions.
***************
*** 4542,4548 ****
        (goto-char (point-min))
        (while (re-search-forward 
                "^[ \t]*\\(pro\\|function\\)[ \t]" nil t)
!         (setq string (buffer-substring 
                        (match-beginning 0)
                        (progn 
                          (idlwave-end-of-statement)
--- 4588,4594 ----
        (goto-char (point-min))
        (while (re-search-forward 
                "^[ \t]*\\(pro\\|function\\)[ \t]" nil t)
!         (setq string (buffer-substring-no-properties
                        (match-beginning 0)
                        (progn 
                          (idlwave-end-of-statement)
***************
*** 5016,5022 ****
  
  (defvar idlwave-shell-temp-pro-file)
  (defvar idlwave-shell-temp-rinfo-save-file)
! (defun idlwave-shell-update-routine-info (&optional quiet run-hooks)
    "Query the shell for routine_info of compiled modules and update the lists."
    ;; Save and compile the procedure.  The compiled procedure is then
    ;; saved into an IDL SAVE file, to allow for fast RESTORE.
--- 5062,5068 ----
  
  (defvar idlwave-shell-temp-pro-file)
  (defvar idlwave-shell-temp-rinfo-save-file)
! (defun idlwave-shell-update-routine-info (&optional quiet run-hooks preempt)
    "Query the shell for routine_info of compiled modules and update the lists."
    ;; Save and compile the procedure.  The compiled procedure is then
    ;; saved into an IDL SAVE file, to allow for fast RESTORE.
***************
*** 5048,5054 ****
     `(progn
        (idlwave-shell-routine-info-filter)
        (idlwave-concatenate-rinfo-lists ,quiet ,run-hooks))
!    'hide))
  
  ;; ---------------------------------------------------------------------------
  ;;
--- 5094,5100 ----
     `(progn
        (idlwave-shell-routine-info-filter)
        (idlwave-concatenate-rinfo-lists ,quiet ,run-hooks))
!    'hide preempt))
  
  ;; ---------------------------------------------------------------------------
  ;;
***************
*** 5127,5133 ****
  
       ;; Check for any special completion functions
       ((and idlwave-complete-special
!          (idlwave-complete-special)))
  
       ((and (idlwave-in-quote)
           (not (eq what 'class)))
--- 5173,5179 ----
  
       ;; Check for any special completion functions
       ((and idlwave-complete-special
!          (idlwave-call-special idlwave-complete-special)))
  
       ((and (idlwave-in-quote)
           (not (eq what 'class)))
***************
*** 5156,5162 ****
         (format "Select a %s name%s"
                 isa
                 (if class-selector
!                    (format " (class is %s)" class-selector)
                   ""))
         isa
         'idlwave-attach-method-classes)))
--- 5202,5210 ----
         (format "Select a %s name%s"
                 isa
                 (if class-selector
!                    (format " (class is %s)" 
!                            (if (eq class-selector t) 
!                                "unknown" class-selector))
                   ""))
         isa
         'idlwave-attach-method-classes)))
***************
*** 5177,5183 ****
         (format "Select a %s name%s"
                 isa
                 (if class-selector
!                    (format " (class is %s)" class-selector)
                   ""))
         isa
         'idlwave-attach-method-classes)))
--- 5225,5233 ----
         (format "Select a %s name%s"
                 isa
                 (if class-selector
!                    (format " (class is %s)" 
!                            (if (eq class-selector t)
!                                "unknown" class-selector))
                   ""))
         isa
         'idlwave-attach-method-classes)))
***************
*** 5264,5276 ****
  If such a function returns `t', *no further* attempts to complete
  other contexts will be done.  If the function returns `nil', other completions
  will be tried.")
! (defun idlwave-complete-special ()
!   (let ((functions idlwave-complete-special)
!       fun)
      (catch 'exit
!       (while (setq fun (pop functions))
!       (if (funcall fun)
!           (throw 'exit t)))
        nil)))
  
  (defun idlwave-make-force-complete-where-list (what &optional module class)
--- 5314,5327 ----
  If such a function returns `t', *no further* attempts to complete
  other contexts will be done.  If the function returns `nil', other completions
  will be tried.")
! 
! (defun idlwave-call-special (functions &rest args)
!   (let ((funcs functions)
!       fun ret)
      (catch 'exit
!       (while (setq fun (pop funcs))
!       (if (setq ret (apply fun args))
!           (throw 'exit ret)))
        nil)))
  
  (defun idlwave-make-force-complete-where-list (what &optional module class)
***************
*** 5522,5535 ****
        (save-excursion (goto-char apos)
                        (looking-at "->[a-zA-Z][a-zA-Z0-9$_]*::")))))
  
  (defun idlwave-determine-class (info type)
!   ;; Determine the class of a routine call.  INFO is the structure returned
!   ;; `idlwave-what-function' or `idlwave-what-procedure'.
!   ;; The third element in this structure is the class.  When nil, we return 
nil.
!   ;; When t, try to get the class from text properties at the arrow.  When
!   ;; the object is "self", we use the class of the current routine.
!   ;; otherwise prompt the user for a class name.  Also stores the selected
!   ;; class as a text property at the arrow.
    ;; TYPE is 'fun or 'pro.
    (let* ((class (nth 2 info))
         (apos (nth 3 info))
--- 5573,5590 ----
        (save-excursion (goto-char apos)
                        (looking-at "->[a-zA-Z][a-zA-Z0-9$_]*::")))))
  
+ (defvar idlwave-determine-class-special nil
+   "List of special functions for determining class.
+ Must accept two arguments: `apos' and `info'")
+ 
  (defun idlwave-determine-class (info type)
!   ;; Determine the class of a routine call.  
!   ;; INFO is the `cw-list' structure as returned by idlwave-where.
!   ;; The second element in this structure is the class.  When nil, we
!   ;; return nil.  When t, try to get the class from text properties at
!   ;; the arrow.  When the object is "self", we use the class of the
!   ;; current routine.  otherwise prompt the user for a class name.
!   ;; Also stores the selected class as a text property at the arrow.
    ;; TYPE is 'fun or 'pro.
    (let* ((class (nth 2 info))
         (apos (nth 3 info))
***************
*** 5550,5556 ****
                               (let ((case-fold-search t))
                                 (looking-at "self\\>")))))
         (force-query idlwave-force-class-query)
!        store class-alist)
      (cond
       ((null class) nil)
       ((eq t class)
--- 5605,5611 ----
                               (let ((case-fold-search t))
                                 (looking-at "self\\>")))))
         (force-query idlwave-force-class-query)
!        store special-class class-alist)
      (cond
       ((null class) nil)
       ((eq t class)
***************
*** 5560,5568 ****
               (not force-query))
          (setq class (get-text-property apos 'idlwave-class)
                class (idlwave-sintern-class class)))
!       (when (and (eq t class)
!                is-self)
!       (setq class (or (nth 2 (idlwave-current-routine)) class)))
        (when (and (eq class t)
                 (or force-query query))
        (setq class-alist 
--- 5615,5634 ----
               (not force-query))
          (setq class (get-text-property apos 'idlwave-class)
                class (idlwave-sintern-class class)))
!       (if (and (eq t class) is-self)
!         (setq class (or (nth 2 (idlwave-current-routine)) class)))
! 
!       ;; Before prompting, try any special class determination routines
!       (when (and (eq t class) 
!                idlwave-determine-class-special
!                (not force-query))
!       (setq special-class 
!             (idlwave-call-special idlwave-determine-class-special apos))
!       (if special-class 
!           (setq class (idlwave-sintern-class special-class)
!                 store idlwave-store-inquired-class)))
!       
!       ;; Prompt for a class, if we need to
        (when (and (eq class t)
                 (or force-query query))
        (setq class-alist 
***************
*** 5582,5592 ****
                                                  type (car info))
                                        ""))
                  class-alist nil nil nil 'idlwave-class-history))))))
        (when (and class (not (eq t class)))
        ;; We have a real class here
        (when (and store arrow)
!         (put-text-property apos (+ apos 2) 'idlwave-class class)
!         (put-text-property apos (+ apos 2) 'face idlwave-class-arrow-face))
        (setf (nth 2 info) class))
        ;; Return the class
        class)
--- 5648,5664 ----
                                                  type (car info))
                                        ""))
                  class-alist nil nil nil 'idlwave-class-history))))))
+ 
+       ;; Store it, if requested
        (when (and class (not (eq t class)))
        ;; We have a real class here
        (when (and store arrow)
!         (condition-case ()
!             (add-text-properties 
!              apos (+ apos 2) 
!              `(idlwave-class ,class face ,idlwave-class-arrow-face 
!                              rear-nonsticky t))
!           (error nil)))
        (setf (nth 2 info) class))
        ;; Return the class
        class)
***************
*** 5678,5684 ****
        (setq cw 'function)
        (save-excursion
        (if (re-search-backward "->[ 
\t]*\\(\\([$a-zA-Z0-9_]+\\)::\\)?[$a-zA-Z0-9_]*\\=" bos t)
!           (setq cw-arrow (match-beginning 0)
                  cw-class (if (match-end 2)
                               (idlwave-sintern-class (match-string 2))
                             t))))))
--- 5750,5756 ----
        (setq cw 'function)
        (save-excursion
        (if (re-search-backward "->[ 
\t]*\\(\\([$a-zA-Z0-9_]+\\)::\\)?[$a-zA-Z0-9_]*\\=" bos t)
!           (setq cw-arrow (copy-marker (match-beginning 0))
                  cw-class (if (match-end 2)
                               (idlwave-sintern-class (match-string 2))
                             t))))))
***************
*** 5698,5705 ****
  
  (defun idlwave-what-function (&optional bound)
    ;; Find out if point is within the argument list of a function.
!   ;; The return value is ("function-name" (point) level).
!   ;; Level is 1 on the to level parenthesis, higher further down.
  
    ;; If the optional BOUND is an integer, bound backwards directed
    ;;    searches to this point.
--- 5770,5777 ----
  
  (defun idlwave-what-function (&optional bound)
    ;; Find out if point is within the argument list of a function.
!   ;; The return value is ("function-name" class arrow-start (point) level).
!   ;; Level is 1 on the top level parentheses, higher further down.
  
    ;; If the optional BOUND is an integer, bound backwards directed
    ;;    searches to this point.
***************
*** 5728,5734 ****
                     pos func-point)
               (if (re-search-backward 
                    "->[ \t]*\\(\\([a-zA-Z][a-zA-Z0-9$_]*\\)::\\)?\\=" bound t)
!                  (setq arrow-start (match-beginning 0)
                         class (or (match-string 2) t)))
               (throw 
                'exit 
--- 5800,5806 ----
                     pos func-point)
               (if (re-search-backward 
                    "->[ \t]*\\(\\([a-zA-Z][a-zA-Z0-9$_]*\\)::\\)?\\=" bound t)
!                  (setq arrow-start (copy-marker (match-beginning 0))
                         class (or (match-string 2) t)))
               (throw 
                'exit 
***************
*** 5752,5760 ****
        (idlwave-start-of-substatement 'pre)
        (setq string (buffer-substring (point) pos))
        (if (string-match 
!          "\\`\\(.*&\\)?[ \t]*\\([a-zA-Z][a-zA-Z0-9$_]*\\)[ \t]*\\(,\\|\\'\\)" 
string)
!         (setq pro (match-string 2 string)
!               pro-point (+ (point) (match-beginning 2)))
        (if (and (idlwave-skip-object)
                 (setq string (buffer-substring (point) pos))
                 (string-match 
--- 5824,5832 ----
        (idlwave-start-of-substatement 'pre)
        (setq string (buffer-substring (point) pos))
        (if (string-match 
!          "\\`[ \t]*\\([a-zA-Z][a-zA-Z0-9$_]*\\)[ \t]*\\(,\\|\\'\\)" string)
!         (setq pro (match-string 1 string)
!               pro-point (+ (point) (match-beginning 1)))
        (if (and (idlwave-skip-object)
                 (setq string (buffer-substring (point) pos))
                 (string-match 
***************
*** 5764,5770 ****
                  pro-point (if (match-beginning 4)
                                (+ (point) (match-beginning 4))
                        pos)
!                 arrow-start (+ (point) (match-beginning 1))
                  class (or (match-string 3 string) t)))))
      (list (idlwave-sintern-routine-or-method pro class)
          (idlwave-sintern-class class)
--- 5836,5842 ----
                  pro-point (if (match-beginning 4)
                                (+ (point) (match-beginning 4))
                        pos)
!                 arrow-start (copy-marker (+ (point) (match-beginning 1)))
                  class (or (match-string 3 string) t)))))
      (list (idlwave-sintern-routine-or-method pro class)
          (idlwave-sintern-class class)
***************
*** 5802,5808 ****
        (goto-char pos)
        nil)))
    
- 
  (defun idlwave-last-valid-char ()
    "Return the last character before point which is not white or a comment
  and also not part of the current identifier.  Since we do this in
--- 5874,5879 ----
***************
*** 5839,5846 ****
  (defun idlwave-complete-in-buffer (type stype list selector prompt isa
                                        &optional prepare-display-function)
    "Perform TYPE completion of word before point against LIST.
! SELECTOR is the PREDICATE argument for the completion function.
! Show PROMPT in echo area.  TYPE is one of 'function, 'procedure or 'keyword."
    (let* ((completion-ignore-case t)
         beg (end (point)) slash part spart completion all-completions
         dpart dcompletion)
--- 5910,5918 ----
  (defun idlwave-complete-in-buffer (type stype list selector prompt isa
                                        &optional prepare-display-function)
    "Perform TYPE completion of word before point against LIST.
! SELECTOR is the PREDICATE argument for the completion function.  Show
! PROMPT in echo area.  TYPE is one of 'function, 'procedure,
! 'class-tag, or 'keyword."
    (let* ((completion-ignore-case t)
         beg (end (point)) slash part spart completion all-completions
         dpart dcompletion)
***************
*** 5869,5875 ****
      (cond
       ((null completion)
        ;; nothing available.
!       (error "Can't find %s completion for \"%s\"" isa part))
       ((and (not (equal dpart dcompletion))
           (not (eq t completion)))
        ;; We can add something
--- 5941,5947 ----
      (cond
       ((null completion)
        ;; nothing available.
!       (error (concat prompt ": no completion for \"%s\"") part))
       ((and (not (equal dpart dcompletion))
           (not (eq t completion)))
        ;; We can add something
***************
*** 5940,5963 ****
      (idlwave-complete-in-buffer 'class 'class (idlwave-class-alist) nil 
                                "Select a class" "class")))
  
! (defun idlwave-attach-classes (list is-kwd show-classes)
    ;; Attach the proper class list to a LIST of completion items.
!   ;; IS-KWD, when non-nil, shows its keywords - otherwise its methods
    ;; SHOW-CLASSES is the value of `idlwave-completion-show-classes'.
!   (catch 'exit
!     (if (or (null show-classes)           ; don't want to see classes
!           (null class-selector)         ; not a method call
!           (and (stringp class-selector) ; the class is already known
!                (not super-classes)))    ; no possibilities for inheritance
!       ;; In these cases, we do not have to do anything
!       (throw 'exit list))
!     
      (let* ((do-prop (and (>= show-classes 0)
                         (>= emacs-major-version 21)))
           (do-buf (not (= show-classes 0)))
!          ; (do-dots (featurep 'xemacs))
           (do-dots t)
!          (inherit (if super-classes
                        (cons class-selector super-classes)))
           (max (abs show-classes))
           (lmax (if do-dots (apply 'max (mapcar 'length list))))
--- 6012,6035 ----
      (idlwave-complete-in-buffer 'class 'class (idlwave-class-alist) nil 
                                "Select a class" "class")))
  
! (defun idlwave-attach-classes (list type show-classes)
    ;; Attach the proper class list to a LIST of completion items.
!   ;; TYPE, when 'kwd, shows classes for method keywords, when
!   ;; 'class-tag, for class tags, and otherwise for methods.
    ;; SHOW-CLASSES is the value of `idlwave-completion-show-classes'.
!   (if (or (null show-classes)           ; don't want to see classes
!         (null class-selector)         ; not a method call
!         (and 
!          (stringp class-selector) ; the class is already known
!          (not super-classes)))    ; no possibilities for inheritance
!       ;; In these cases, we do not have to do anything
!       list
      (let* ((do-prop (and (>= show-classes 0)
                         (>= emacs-major-version 21)))
           (do-buf (not (= show-classes 0)))
!          ;; (do-dots (featurep 'xemacs))
           (do-dots t)
!          (inherit (if (and (not (eq type 'class-tag)) super-classes)
                        (cons class-selector super-classes)))
           (max (abs show-classes))
           (lmax (if do-dots (apply 'max (mapcar 'length list))))
***************
*** 5965,5980 ****
        (mapcar 
         (lambda (x)
         ;; get the classes
!        (setq classes
!              (if is-kwd 
!                  (idlwave-all-method-keyword-classes
!                   method-selector x type-selector)
!                (idlwave-all-method-classes x type-selector)))
!        (if inherit
!            (setq classes 
!                  (delq nil
!                        (mapcar (lambda (x) (if (memq x inherit) x nil))
!                                classes))))
         (setq nclasses (length classes))
         ;; Make the separator between item and class-info
         (if do-dots
--- 6037,6058 ----
        (mapcar 
         (lambda (x)
         ;; get the classes
!        (if (eq type 'class-tag)
!            ;; Just one class for tags
!            (setq classes
!                  (list 
!                   (idlwave-class-or-superclass-with-tag class-selector x)))
!          ;; Multiple classes for method of method-keyword
!          (setq classes
!                (if (eq type 'kwd)
!                    (idlwave-all-method-keyword-classes
!                     method-selector x type-selector)
!                  (idlwave-all-method-classes x type-selector)))
!          (if inherit
!              (setq classes 
!                    (delq nil
!                          (mapcar (lambda (x) (if (memq x inherit) x nil))
!                                  classes)))))
         (setq nclasses (length classes))
         ;; Make the separator between item and class-info
         (if do-dots
***************
*** 6001,6010 ****
  
  (defun idlwave-attach-method-classes (list)
    ;; Call idlwave-attach-classes with method parameters
!   (idlwave-attach-classes list nil idlwave-completion-show-classes))
  (defun idlwave-attach-keyword-classes (list)
    ;; Call idlwave-attach-classes with keyword parameters
!   (idlwave-attach-classes list t idlwave-completion-show-classes))
  
  ;;----------------------------------------------------------------------
  ;;----------------------------------------------------------------------
--- 6079,6092 ----
  
  (defun idlwave-attach-method-classes (list)
    ;; Call idlwave-attach-classes with method parameters
!   (idlwave-attach-classes list 'method idlwave-completion-show-classes))
  (defun idlwave-attach-keyword-classes (list)
    ;; Call idlwave-attach-classes with keyword parameters
!   (idlwave-attach-classes list 'kwd idlwave-completion-show-classes))
! (defun idlwave-attach-class-tag-classes (list)
!   ;; Call idlwave-attach-classes with class structure tags
!   (idlwave-attach-classes list 'class-tag idlwave-completion-show-classes))
!                                       
  
  ;;----------------------------------------------------------------------
  ;;----------------------------------------------------------------------
***************
*** 6163,6168 ****
--- 6245,6257 ----
        (remove-text-properties beg (point) '(face nil))))
    (eval idlwave-complete-after-success-form-force))
  
+ (defun idlwave-keyboard-quit ()
+   (interactive)
+   (unwind-protect
+       (if (eq (car-safe last-command) 'idlwave-display-completion-list)
+         (idlwave-restore-wconf-after-completion))
+     (keyboard-quit)))
+ 
  (defun idlwave-restore-wconf-after-completion ()
    "Restore the old (before completion) window configuration."
    (and idlwave-completion-restore-window-configuration
***************
*** 6215,6221 ****
                                    (setq this-command last-command)))
      new-map))
  
! ;; In Emacs we also to replace choose keybindings in the completion
  ;; map in order to install our wrappers.
  
  (defun idlwave-display-completion-list-emacs (list)
--- 6304,6310 ----
                                    (setq this-command last-command)))
      new-map))
  
! ;; In Emacs we also replace keybindings in the completion
  ;; map in order to install our wrappers.
  
  (defun idlwave-display-completion-list-emacs (list)
***************
*** 6271,6284 ****
           (end (cdr borders))
           tags)
        (goto-char beg)
!       (while (re-search-forward "[{,][ \t]*\\(\\$.*\n[ 
\t]*\\)?\\([a-zA-Z][a-zA-Z0-9_]*\\)[ \t]*:" end t)
        ;; Check if we are still on the top level of the structure.
        (if (and (condition-case nil (progn (up-list -1) t) (error nil))
                 (= (point) beg))
!           (push (match-string 2) tags))
        (goto-char (match-end 0)))
        (nreverse tags))))
  
  (defun idlwave-struct-inherits ()
    "Return a list of all `inherits' names in the struct at point.
  Point is expected just before the opening `{' of the struct definition."
--- 6360,6382 ----
           (end (cdr borders))
           tags)
        (goto-char beg)
!       (while (re-search-forward "[{,][ \t]*\\(\\$.*\n\\(^[ \t]*\\(\\$[ 
\t]*\\)?\\(;.*\\)?\n\\)*[ \t]*\\)?\\([a-zA-Z][a-zA-Z0-9_]*\\)[ \t]*:" end t)
        ;; Check if we are still on the top level of the structure.
        (if (and (condition-case nil (progn (up-list -1) t) (error nil))
                 (= (point) beg))
!           (push (match-string 5) tags))
        (goto-char (match-end 0)))
        (nreverse tags))))
  
+ (defun idlwave-find-struct-tag (tag)
+   "Find a given TAG in the structure defined at point."
+   (let* ((borders (idlwave-struct-borders))
+        (beg (car borders))
+        (end (cdr borders))
+        (case-fold-search t))
+     (re-search-forward (concat "\\(^[ \t]*\\|[,{][ \t]*\\)" tag "[ \t]*:") 
+                      end t)))
+ 
  (defun idlwave-struct-inherits ()
    "Return a list of all `inherits' names in the struct at point.
  Point is expected just before the opening `{' of the struct definition."
***************
*** 6324,6330 ****
  integer, limit the search.  If BOUND is the symbol `all', we search
  first back and then forward through the entire file.  If BOUND is the
  symbol `back' we search only backward."
!   (let* ((ws "[ \t]*\\(\\$.*\n[ \t]*\\)?")
         (case-fold-search t)
         (lim (if (integerp bound) bound nil))
         (re (concat
--- 6422,6428 ----
  integer, limit the search.  If BOUND is the symbol `all', we search
  first back and then forward through the entire file.  If BOUND is the
  symbol `back' we search only backward."
!   (let* ((ws "[ \t]*\\(\\$.*\n[ \t]*\\)*")
         (case-fold-search t)
         (lim (if (integerp bound) bound nil))
         (re (concat
***************
*** 6372,6377 ****
--- 6470,6482 ----
        (setcdr inherits (mapcar (lambda (x) (idlwave-sintern-class x 'set))
                                 (cdr inherits))))))
  
+ (defun idlwave-find-class-definition (class)
+   (let ((case-fold-search t))
+     (if (re-search-forward
+        (concat "^[ \t]*pro[ \t]+" (downcase class) "__define" "\\>") nil t)
+       ;; FIXME: should we limit to end of pro here?
+       (idlwave-find-structure-definition nil class))))
+ 
  (defun idlwave-find-class-info (class)
    "Find the __define procedure for a class structure and return info entry."
    (let* ((pro (concat (downcase class) "__define"))
***************
*** 6394,6407 ****
          (insert-file-contents file))
        (save-excursion
          (goto-char 1)
!         (setq case-fold-search t)
!         (when (and (re-search-forward
!                     (concat "^[ \t]*pro[ \t]+" pro "\\>") nil t)
!                    ;; FIXME: should we limit to end of pro here?
!                    (idlwave-find-structure-definition nil class))
!           (list class
!                 (cons 'tags (idlwave-struct-tags))
!                 (cons 'inherits (idlwave-struct-inherits)))))))))
  
  (defun idlwave-class-tags (class)
    "Return the native tags in CLASS."
--- 6499,6508 ----
          (insert-file-contents file))
        (save-excursion
          (goto-char 1)
!         (if (idlwave-find-class-definition class)
!             (list class
!                   (cons 'tags (idlwave-struct-tags))
!                   (cons 'inherits (idlwave-struct-inherits)))))))))
  
  (defun idlwave-class-tags (class)
    "Return the native tags in CLASS."
***************
*** 6412,6419 ****
  
  (defun idlwave-all-class-tags (class)
    "Return a list of native and inherited tags in CLASS."
!   (apply 'append (mapcar 'idlwave-class-tags
!                        (cons class (idlwave-all-class-inherits class)))))
  
  (defun idlwave-all-class-inherits (class)
    "Return a list of all superclasses of CLASS (recursively expanded).
--- 6513,6525 ----
  
  (defun idlwave-all-class-tags (class)
    "Return a list of native and inherited tags in CLASS."
!   (condition-case err
!       (apply 'append (mapcar 'idlwave-class-tags
!                            (cons class (idlwave-all-class-inherits class))))
!     (error           
!      (idlwave-class-tag-reset)
!      (error "%s" (error-message-string err)))))
! 
  
  (defun idlwave-all-class-inherits (class)
    "Return a list of all superclasses of CLASS (recursively expanded).
***************
*** 6427,6438 ****
          entry)
        (if (setq entry (assq 'all-inherits info))
          (cdr entry)
!       (let ((inherits (idlwave-class-inherits class))
              rtn all-inherits cl)
          (while inherits
            (setq cl (pop inherits)
!                 rtn (cons cl rtn)
!                 inherits (append inherits (idlwave-class-inherits cl))))
          (setq all-inherits (nreverse rtn))
          (nconc info (list (cons 'all-inherits all-inherits)))
          all-inherits))))))
--- 6533,6553 ----
          entry)
        (if (setq entry (assq 'all-inherits info))
          (cdr entry)
!       ;; Save the depth of inheritance scan to check for circular references
!       (let ((inherits (mapcar (lambda (x) (cons x 0))
!                               (idlwave-class-inherits class)))
              rtn all-inherits cl)
          (while inherits
            (setq cl (pop inherits)
!                 rtn (cons (car cl) rtn)
!                 inherits (append (mapcar (lambda (x)
!                                            (cons x (1+ (cdr cl))))
!                                          (idlwave-class-inherits (car cl)))
!                                  inherits))
!           (if (> (cdr cl) 999)
!             (error
!              "Class scan: inheritance depth exceeded. Circular inheritance?")
!             ))
          (setq all-inherits (nreverse rtn))
          (nconc info (list (cons 'all-inherits all-inherits)))
          all-inherits))))))
***************
*** 6446,6455 ****
  (defvar idlwave-current-tags-class nil)
  (defvar idlwave-current-class-tags nil)
  (defvar idlwave-current-native-class-tags nil)
! (defvar idlwave-sint-classtags nil)
! (idlwave-new-sintern-type 'classtag)
  (add-to-list 'idlwave-complete-special 'idlwave-complete-class-structure-tag)
! (add-hook 'idlwave-update-rinfo-hook 'idlwave-classtag-reset)
  
  (defun idlwave-complete-class-structure-tag ()
    "Complete a structure tag on a `self' argument in an object method."
--- 6561,6570 ----
  (defvar idlwave-current-tags-class nil)
  (defvar idlwave-current-class-tags nil)
  (defvar idlwave-current-native-class-tags nil)
! (defvar idlwave-sint-class-tags nil)
! (idlwave-new-sintern-type 'class-tag)
  (add-to-list 'idlwave-complete-special 'idlwave-complete-class-structure-tag)
! (add-hook 'idlwave-update-rinfo-hook 'idlwave-class-tag-reset)
  
  (defun idlwave-complete-class-structure-tag ()
    "Complete a structure tag on a `self' argument in an object method."
***************
*** 6461,6493 ****
          (skip-chars-backward "[a-zA-Z0-9._$]")
          (and (< (point) (- pos 4))
               (looking-at "self\\.")))
!       (let* ((class (nth 2 (idlwave-current-routine))))
          ;; Check if we are in a class routine
!         (unless class
            (error "Not in a method procedure or function"))
          ;; Check if we need to update the "current" class
!         (if (not (equal class idlwave-current-tags-class))
!             (idlwave-prepare-class-tag-completion class))
!         (setq idlwave-completion-help-info nil)
          (let  ((idlwave-cpl-bold idlwave-current-native-class-tags))
            (idlwave-complete-in-buffer
!            'classtag 'classtag 
             idlwave-current-class-tags nil
!            (format "Select a tag of class %s" class)
!            "class tag"))
          t) ; return t to skip other completions
        nil)))
  
! (defun idlwave-classtag-reset ()
    (setq idlwave-current-tags-class nil))
  
  (defun idlwave-prepare-class-tag-completion (class)
    "Find and parse the necessary class definitions for class structure tags."
!   (setq idlwave-sint-classtags nil)
    (setq idlwave-current-tags-class class)
    (setq idlwave-current-class-tags
        (mapcar (lambda (x)
!                 (list (idlwave-sintern-classtag x 'set)))
                (idlwave-all-class-tags class)))
    (setq idlwave-current-native-class-tags
        (mapcar 'downcase (idlwave-class-tags class))))
--- 6576,6614 ----
          (skip-chars-backward "[a-zA-Z0-9._$]")
          (and (< (point) (- pos 4))
               (looking-at "self\\.")))
!       (let* ((class-selector (nth 2 (idlwave-current-routine)))
!              (super-classes (idlwave-all-class-inherits class-selector)))
          ;; Check if we are in a class routine
!         (unless class-selector
            (error "Not in a method procedure or function"))
          ;; Check if we need to update the "current" class
!         (if (not (equal class-selector idlwave-current-tags-class))
!             (idlwave-prepare-class-tag-completion class-selector))
!         (setq idlwave-completion-help-info 
!               (list 'idlwave-complete-class-structure-tag-help
!                     (idlwave-sintern-routine 
!                      (concat class-selector "__define"))
!                     nil))
          (let  ((idlwave-cpl-bold idlwave-current-native-class-tags))
            (idlwave-complete-in-buffer
!            'class-tag 'class-tag 
             idlwave-current-class-tags nil
!            (format "Select a tag of class %s" class-selector)
!            "class tag"
!            'idlwave-attach-class-tag-classes))
          t) ; return t to skip other completions
        nil)))
  
! (defun idlwave-class-tag-reset ()
    (setq idlwave-current-tags-class nil))
  
  (defun idlwave-prepare-class-tag-completion (class)
    "Find and parse the necessary class definitions for class structure tags."
!   (setq idlwave-sint-class-tags nil)
    (setq idlwave-current-tags-class class)
    (setq idlwave-current-class-tags
        (mapcar (lambda (x)
!                 (list (idlwave-sintern-class-tag x 'set)))
                (idlwave-all-class-tags class)))
    (setq idlwave-current-native-class-tags
        (mapcar 'downcase (idlwave-class-tags class))))
***************
*** 6549,6554 ****
--- 6670,6677 ----
             t)) ; return t to skip other completions
          (t nil))))
  
+ ;; Here we fake help using the routine "system variables" with keyword
+ ;; set to the sysvar.  Name and kwd are global variables here.
  (defvar name) 
  (defvar kwd)
  (defun idlwave-complete-sysvar-help (mode word)
***************
*** 6566,6572 ****
                          (nth 1 idlwave-completion-help-info)
                        word))))
     (t (error "This should not happen"))))
!                         
  
  (defun idlwave-sysvars-reset ()
    (if (and (fboundp 'idlwave-shell-is-running)
--- 6689,6731 ----
                          (nth 1 idlwave-completion-help-info)
                        word))))
     (t (error "This should not happen"))))
! 
! ;; Fake help in the source buffer for class structure tags.
! ;; kwd and name are global-variables here.
! (defvar idlwave-help-do-class-struct-tag nil)
! (defun idlwave-complete-class-structure-tag-help (mode word)
!   (cond
!    ((eq mode 'test) ; nothing gets fontified for class tags
!     nil)
!    ((eq mode 'set)
!     (let (class-with)
!       (when (setq class-with 
!               (idlwave-class-or-superclass-with-tag 
!                idlwave-current-tags-class
!                word))
!       (if (assq (idlwave-sintern-class class-with) 
!                 idlwave-system-class-info)
!           (error "No help available for system class tags."))
!       (setq name (concat class-with "__define"))))
!     (setq kwd word
!         idlwave-help-do-class-struct-tag t))
!    (t (error "This should not happen"))))
! 
! (defun idlwave-class-or-superclass-with-tag (class tag)
!   "Find and return the CLASS or one of its superclass with the
! associated TAG, if any."
!   (let ((sclasses (cons class (cdr (assq 'all-inherits 
!                                        (idlwave-class-info class)))))
!       cl)
!    (catch 'exit
!      (while sclasses
!        (setq cl (pop sclasses))
!        (let ((tags (idlwave-class-tags cl)))
!        (while tags
!          (if (eq t (compare-strings tag 0 nil (car tags) 0 nil t))
!            (throw 'exit cl))         
!          (setq tags (cdr tags))))))))
! 
  
  (defun idlwave-sysvars-reset ()
    (if (and (fboundp 'idlwave-shell-is-running)
***************
*** 6620,6628 ****
        (set-buffer "*Completions*")
        (save-excursion
        (goto-char (point-min))
!       (while (re-search-forward "\\.*<[^>]+>" nil t)
!         (put-text-property (match-beginning 0) (match-end 0)
!                            'face 'font-lock-string-face))))))
  
  (defun idlwave-uniquify (list)
    (let (nlist)
--- 6779,6788 ----
        (set-buffer "*Completions*")
        (save-excursion
        (goto-char (point-min))
!       (let ((buffer-read-only nil))
!         (while (re-search-forward "\\.*<[^>]+>" nil t)
!           (put-text-property (match-beginning 0) (match-end 0)
!                              'face 'font-lock-string-face)))))))
  
  (defun idlwave-uniquify (list)
    (let (nlist)
***************
*** 6676,6685 ****
  (defvar idlwave-last-context-help-pos nil)
  (defun idlwave-context-help (&optional arg)
    "Display IDL Online Help on context.
! If point is on a keyword, help for that keyword will be shown.
! If point is on a routine name or in the argument list of a routine,
! help for that routine will be displayed.
! Works for system routines and keywords only."
    (interactive "P")
    (idlwave-require-online-help)
    (idlwave-do-context-help arg))
--- 6836,6848 ----
  (defvar idlwave-last-context-help-pos nil)
  (defun idlwave-context-help (&optional arg)
    "Display IDL Online Help on context.
! If point is on a keyword, help for that keyword will be shown.  If
! point is on a routine name or in the argument list of a routine, help
! for that routine will be displayed.  Works for system routines and
! keywords, it pulls up text help.  For other routies and keywords,
! visits the source file, finding help in the header (if
! `idlwave-help-source-try-header' is non-nil) or the routine definition
! itself."
    (interactive "P")
    (idlwave-require-online-help)
    (idlwave-do-context-help arg))
***************
*** 6711,6717 ****
    (if idlwave-help-is-loaded
        t  ;; everything is OK.
      (let* ((dir (or (idlwave-help-directory)
!                   (error "Online Help is not installed 
(idlwave-help-directory is unknown)")))
           (lfile1 (expand-file-name "idlw-help.elc" dir))
           (lfile2 (expand-file-name "idlw-help.el" dir))
           (hfile (expand-file-name "idlw-help.txt" dir)))
--- 6874,6880 ----
    (if idlwave-help-is-loaded
        t  ;; everything is OK.
      (let* ((dir (or (idlwave-help-directory)
!                   (error "Online Help not installed (help directory unknown) 
- download at idlwave.org")))
           (lfile1 (expand-file-name "idlw-help.elc" dir))
           (lfile2 (expand-file-name "idlw-help.el" dir))
           (hfile (expand-file-name "idlw-help.txt" dir)))




reply via email to

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