lean2/src/emacs/lean-mode.el

116 lines
5.3 KiB
EmacsLisp
Raw Normal View History

;; Copyright (c) 2013, 2014 Microsoft Corporation. All rights reserved.
;; Released under Apache 2.0 license as described in the file LICENSE.
;;
;; Author: Leonardo de Moura
;; Soonho Kong
;;
(require 'cl-lib)
(require 'generic-x)
(require 'compile)
(require 'flymake)
2014-08-14 00:02:49 +00:00
(require 'lean-variable)
(require 'lean-util)
(require 'lean-settings)
(require 'lean-flycheck)
(require 'lean-input)
2014-08-14 00:02:49 +00:00
(require 'lean-type)
2014-08-16 03:48:30 +00:00
(require 'lean-tags)
(defun lean-compile-string (exe-name args file-name)
"Concatenate exe-name, args, and file-name"
(format "%s %s %s" exe-name args file-name))
2014-08-14 00:02:49 +00:00
(defun lean-create-temp-in-system-tempdir (file-name prefix)
"Create a temp lean file and return its name"
(make-temp-file (or prefix "flymake") nil ".lean"))
(defun lean-execute (&optional arg)
"Execute Lean in the current buffer"
(interactive "sarg: ")
(let ((target-file-name
2014-08-14 00:02:49 +00:00
(or
(buffer-file-name)
(flymake-init-create-temp-buffer-copy 'lean-create-temp-in-system-tempdir))))
(compile (lean-compile-string
(lean-get-executable lean-executable-name)
(or arg "")
target-file-name))))
(defun lean-std-exe ()
(interactive)
(lean-execute))
(defun lean-hott-exe ()
(interactive)
(lean-execute "--hott"))
(defun lean-set-keys ()
(local-set-key "\C-c\C-x" 'lean-std-exe)
(local-set-key "\C-c\C-l" 'lean-std-exe)
2014-08-14 00:02:49 +00:00
(local-set-key "\C-c\C-k" 'lean-hott-exe)
(local-set-key "\C-c\C-t" 'lean-eldoc-documentation-function)
2014-08-16 03:48:30 +00:00
(local-set-key "\C-c\C-f" 'lean-fill-placeholder)
(local-set-key "\M-." 'lean-find-tag)
(local-set-key [tab] 'lean-complete-tag))
(define-abbrev-table 'lean-mode-abbrev-table '(
("var" "variable")
("vars" "variables")
("def" "definition")
2014-08-16 03:48:30 +00:00
("th" "theorem")))
(define-generic-mode
'lean-mode ;; name of the mode to create
'("--") ;; comments start with
'("import" "abbreviation" "opaque_hint" "tactic_hint" "definition" "renaming" "inline" "hiding" "exposing" "parameter" "parameters" "proof" "qed" "conjecture" "hypothesis" "lemma" "corollary" "variable" "variables" "print" "theorem" "axiom" "inductive" "with" "structure" "universe" "alias" "help" "environment" "options" "precedence" "postfix" "prefix" "calc_trans" "calc_subst" "calc_refl" "infix" "infixl" "infixr" "notation" "eval" "check" "exit" "coercion" "end" "private" "using" "namespace" "builtin" "including" "instance" "section" "set_option" "add_rewrite" "extends") ;; some keywords
'(("\\_<\\(bool\\|int\\|nat\\|real\\|Prop\\|Type\\|\\|\\)\\_>" . 'font-lock-type-face)
("\\_<\\(calc\\|have\\|obtains\\|show\\|by\\|in\\|let\\|forall\\|fun\\|exists\\|if\\|then\\|else\\|assume\\|take\\|obtain\\|from\\)\\_>" . font-lock-keyword-face)
("\"[^\"]*\"" . 'font-lock-string-face)
("\\(->\\|↔\\|/\\\\\\|==\\|\\\\/\\|[*+/<=>¬∧∨≠≤≥-]\\)" . 'font-lock-constant-face)
("\\\\|→\\|∃\\|∀\\|:\\|:=\\)" . font-lock-constant-face)
("\\_<\\(\\b.*_tac\\|Cond\\|or_else\\|t\\(?:hen\\|ry\\)\\|when\\|assumption\\|apply\\|b\\(?:ack\\|eta\\)\\|done\\|exact\\)\\_>" . 'font-lock-constant-face)
("\\_<\\(universe\\|inductive\\|theorem\\|axiom\\|lemma\\|hypothesis\\|abbreviation\\|definition\\|variable\\|parameter\\)\\_>[ \t\{\[]*\\([^ \t\n]*\\)" (2 'font-lock-function-name-face))
("\\_<\\(variables\\|parameters\\)\\_>[ \t\(\{\[]*\\([^:]*\\)" (2 'font-lock-function-name-face))
("\\(set_opaque\\|set_option\\)[ \t]*\\([^ \t\n]*\\)" (2 'font-lock-constant-face))
("\\_<_\\_>" . 'font-lock-preprocessor-face)
("\\_<sorry\\_>" . 'font-lock-warning-face)
;;
)
'("\\.lean$") ;; files for which to activate this mode
'((lambda()
(set-input-method "Lean")
(set (make-local-variable 'lisp-indent-function)
'common-lisp-indent-function)
(lean-set-keys)
(setq local-abbrev-table lean-mode-abbrev-table)
(abbrev-mode 1)
2014-08-14 00:02:49 +00:00
(add-hook 'before-change-functions '
lean-before-change-function nil t)
(add-hook 'after-change-functions '
lean-after-change-function nil t)
;; Draw a vertical line for rule-column
(when (and lean-rule-column
lean-show-rule-column-method)
(cl-case lean-show-rule-column-method
('vline (require 'fill-column-indicator)
(setq fci-rule-column lean-rule-column)
(setq fci-rule-color lean-rule-color)
2014-08-14 00:02:49 +00:00
(add-hook 'lean-mode-hook 'fci-mode nil t))))
;; Delete Trailing Whitespace
(if lean-delete-trailing-whitespace
(progn (require 'whitespace-cleanup-mode)
2014-08-14 00:02:49 +00:00
(add-hook 'lean-mode-hook 'whitespace-cleanup-mode nil t))
(remove-hook 'lean-mode-hook 'whitespace-cleanup-mode))
2014-08-14 00:02:49 +00:00
;; eldoc
(set (make-local-variable 'eldoc-documentation-function)
2014-08-14 13:22:01 +00:00
'lean-eldoc-documentation-function)
2014-08-14 00:02:49 +00:00
(eldoc-mode +1)
))
"A mode for Lean files" ;; doc string for this mode
)
(provide 'lean-mode)
; (regexp-opt '("Int" "Bool" "Nat" "Type" "Real") t)
; (regexp-opt '("let" "in" "have" "calc" "forall" "exists") t)
; (regexp-opt '("=" "->" "≠" "" "∧" "¬" "/\\" "\\/" "+" "-" "*" "/" "<" ">" "≤" "≥" "==" "∀" "∃" "→" "λ" ":") t)
; (regexp-opt '("apply" "exact" "trivial" "absurd" "beta" "apply" "unfold" "done" "back" "Try" "Then" "OrElse" "OrElse" "Cond" "When" "unfold_all" ) t)