PageRenderTime 68ms CodeModel.GetById 28ms RepoModel.GetById 1ms app.codeStats 0ms

/vendor/haskell-mode/haskell-doc.el

http://github.com/rejeep/emacs
Emacs Lisp | 1972 lines | 1185 code | 174 blank | 613 comment | 23 complexity | 5660d9174cec87faa101fe3d02e8eca0 MD5 | raw file
Possible License(s): GPL-2.0
  1. ;;; haskell-doc.el --- show function types in echo area -*- coding: iso-8859-1 -*-
  2. ;; Copyright (C) 2004, 2005, 2006, 2007, 2009 Free Software Foundation, Inc.
  3. ;; Copyright (C) 1997 Hans-Wolfgang Loidl
  4. ;; Author: Hans-Wolfgang Loidl <hwloidl@dcs.glasgow.ac.uk>
  5. ;; Temporary Maintainer and Hacker: Graeme E Moss <gem@cs.york.ac.uk>
  6. ;; Keywords: extensions, minor mode, language mode, Haskell
  7. ;; Created: 1997-06-17
  8. ;; URL: http://cvs.haskell.org/cgi-bin/cvsweb.cgi/fptools/CONTRIB/haskell-modes/emacs/haskell-doc.el?rev=HEAD
  9. ;;; Copyright:
  10. ;; ==========
  11. ;; This program is free software; you can redistribute it and/or modify
  12. ;; it under the terms of the GNU General Public License as published by
  13. ;; the Free Software Foundation; either version 3, or (at your option)
  14. ;; any later version.
  15. ;;
  16. ;; This program is distributed in the hope that it will be useful,
  17. ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
  18. ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  19. ;; GNU General Public License for more details.
  20. ;;
  21. ;; You should have received a copy of the GNU General Public License
  22. ;; along with this program; if not, you can either send email to this
  23. ;; program's maintainer or write to: The Free Software Foundation,
  24. ;; Inc.; 59 Temple Place, Suite 330; Boston, MA 02111-1307, USA.
  25. ;;; Commentary:
  26. ;; ===========
  27. ;; This program shows the type of the Haskell function under the cursor in the
  28. ;; minibuffer. It acts as a kind of "Emacs background process", by regularly
  29. ;; checking the word under the cursor and matching it against a list of
  30. ;; prelude, library, local and global functions.
  31. ;; To show types of global functions, i.e. functions defined in a module
  32. ;; imported by the current module, call the function
  33. ;; `turn-on-haskell-doc-global-types'. This automatically loads all modules
  34. ;; and builds `imenu' tables to get the types of all functions.
  35. ;; Note: The modules are loaded recursively, so you might pull in
  36. ;; many modules by just turning on global function support.
  37. ;; This features is currently not very well supported.
  38. ;; This program was inspired by the `eldoc.el' package by Noah Friedman.
  39. ;;; Installation:
  40. ;; =============
  41. ;; One useful way to enable this minor mode is to put the following in your
  42. ;; .emacs:
  43. ;;
  44. ;; (autoload 'turn-on-haskell-doc-mode "haskell-doc" nil t)
  45. ;; and depending on the major mode you use for your Haskell programs:
  46. ;; (add-hook 'hugs-mode-hook 'turn-on-haskell-doc-mode) ; hugs-mode
  47. ;; or
  48. ;; (add-hook 'haskell-mode-hook 'turn-on-haskell-doc-mode) ; haskell-mode
  49. ;;; Customisation:
  50. ;; ==============
  51. ;; You can control what exactly is shown by setting the following variables to
  52. ;; either t or nil:
  53. ;; `haskell-doc-show-global-types' (default: nil)
  54. ;; `haskell-doc-show-reserved' (default: t)
  55. ;; `haskell-doc-show-prelude' (default: t)
  56. ;; `haskell-doc-show-strategy' (default: t)
  57. ;; `haskell-doc-show-user-defined' (default: t)
  58. ;; If you want to define your own strings for some identifiers define an
  59. ;; alist of (ID . STRING) and set `haskell-doc-show-user-defined' to t.
  60. ;; E.g:
  61. ;;
  62. ;; (setq haskell-doc-show-user-defined t)
  63. ;; (setq haskell-doc-user-defined-ids
  64. ;; (list
  65. ;; '("main" . "just another pathetic main function")
  66. ;; '("foo" . "a very dummy name")
  67. ;; '("bar" . "another dummy name")))
  68. ;; The following two variables are useful to make the type fit on one line:
  69. ;; If `haskell-doc-chop-off-context' is non-nil the context part of the type
  70. ;; of a local fct will be eliminated (default: t).
  71. ;; If `haskell-doc-chop-off-fctname' is non-nil the function name is not
  72. ;; shown together with the type (default: nil).
  73. ;;; Internals:
  74. ;; ==========
  75. ;; `haskell-doc-mode' is implemented as a minor-mode. So, you can combine it
  76. ;; with any other mode. To enable it just type
  77. ;; M-x turn-on-haskell-doc-mode
  78. ;; These are the names of the functions that can be called directly by the
  79. ;; user (with keybindings in `haskell-hugs-mode' and `haskell-mode'):
  80. ;; `haskell-doc-mode' ... toggle haskell-doc-mode; with prefix turn it on
  81. ;; unconditionally if the prefix is greater 0 otherwise
  82. ;; turn it off
  83. ;; Key: CTRL-c CTRL-o (CTRL-u CTRL-c CTRL-o)
  84. ;; `haskell-doc-ask-mouse-for-type' ... show the type of the id under the mouse
  85. ;; Key: C-S-M-mouse-3
  86. ;; `haskell-doc-show-reserved' ... toggle echoing of reserved id's types
  87. ;; `haskell-doc-show-prelude' ... toggle echoing of prelude id's types
  88. ;; `haskell-doc-show-strategy' ... toggle echoing of strategy id's types
  89. ;; `haskell-doc-show-user-defined' ... toggle echoing of user def id's types
  90. ;; `haskell-doc-check-active' ... check whether haskell-doc is active;
  91. ;; Key: CTRL-c ESC-/
  92. ;;; ToDo:
  93. ;; =====
  94. ;; - Fix byte-compile problems in `haskell-doc-prelude-types' for getArgs etc
  95. ;; - Write a parser for .hi files and make haskell-doc independent from
  96. ;; hugs-mode. Read library interfaces via this parser.
  97. ;; - Indicate kind of object with colours
  98. ;; - Handle multi-line types
  99. ;; - Encode i-am-fct info in the alist of ids and types.
  100. ;;; Bugs:
  101. ;; =====
  102. ;; - Some prelude fcts aren't displayed properly. This might be due to a
  103. ;; name clash of Haskell and Elisp functions (e.g. length) which
  104. ;; confuses Emacs when reading `haskell-doc-prelude-types'
  105. ;;; Changelog:
  106. ;; ==========
  107. ;; $Log: haskell-doc.el,v $
  108. ;; Revision 1.30 2009/02/02 21:00:33 monnier
  109. ;; (haskell-doc-imported-list): Don't add current buffer
  110. ;; to the imported file list if it is not (yet?) visiting a file.
  111. ;;
  112. ;; Revision 1.29 2007-12-12 04:04:19 monnier
  113. ;; (haskell-doc-in-code-p): New function.
  114. ;; (haskell-doc-show-type): Use it.
  115. ;;
  116. ;; Revision 1.28 2007/08/30 03:10:08 monnier
  117. ;; Comment/docs fixes.
  118. ;;
  119. ;; Revision 1.27 2007/07/30 17:36:50 monnier
  120. ;; (displayed-month): Remove declaration since it's not used here.
  121. ;;
  122. ;; Revision 1.26 2007/02/10 06:28:55 monnier
  123. ;; (haskell-doc-get-current-word): Remove.
  124. ;; Change all refs to it, to use haskell-ident-at-point instead.
  125. ;;
  126. ;; Revision 1.25 2007/02/09 21:53:42 monnier
  127. ;; (haskell-doc-get-current-word): Correctly distinguish
  128. ;; variable identifiers and infix identifiers.
  129. ;; (haskell-doc-rescan-files): Avoid switch-to-buffer.
  130. ;; (haskell-doc-imported-list): Operate on current buffer.
  131. ;; (haskell-doc-make-global-fct-index): Adjust call.
  132. ;;
  133. ;; Revision 1.24 2006/11/20 20:18:24 monnier
  134. ;; (haskell-doc-mode-print-current-symbol-info): Fix thinko.
  135. ;;
  136. ;; Revision 1.23 2006/10/20 03:12:31 monnier
  137. ;; Drop post-command-idle-hook in favor of run-with-idle-timer.
  138. ;; (haskell-doc-timer, haskell-doc-buffers): New vars.
  139. ;; (haskell-doc-mode): Use them.
  140. ;; (haskell-doc-check-active): Update the check.
  141. ;; (haskell-doc-mode-print-current-symbol-info): Remove the interactive spec.
  142. ;; Don't sit-for unless it's really needed.
  143. ;;
  144. ;; Revision 1.22 2006/09/20 18:42:35 monnier
  145. ;; Doc fix.
  146. ;;
  147. ;; Revision 1.21 2005/11/21 21:48:52 monnier
  148. ;; * haskell-doc.el (haskell-doc-extract-types): Get labelled data working.
  149. ;; (haskell-doc-prelude-types): Update via auto-generation.
  150. ;;
  151. ;; * haskell-doc.el (haskell-doc-extract-types): Get it partly working.
  152. ;; (haskell-doc-fetch-lib-urls): Don't use a literal if we apply
  153. ;; `nreverse' on it later on.
  154. ;; (haskell-doc-prelude-types): Update some parts by auto-generation.
  155. ;; (haskell-doc-grab, haskell-doc-string-nub-ws): Simplify.
  156. ;;
  157. ;; * haskell-doc.el (haskell-doc-maintainer, haskell-doc-varlist)
  158. ;; (haskell-doc-submit-bug-report, haskell-doc-ftp-site)
  159. ;; (haskell-doc-visit-home): Remove.
  160. ;; (haskell-doc-reserved-ids, haskell-doc-fetch-lib-urls)
  161. ;; (haskell-doc-extract-and-insert-types): New funs.
  162. ;; (haskell-doc-reserved-ids): Fix type of `map'.
  163. ;;
  164. ;; Revision 1.20 2005/11/21 21:27:57 monnier
  165. ;; (haskell-doc-extract-types): Get labelled data working.
  166. ;; (haskell-doc-prelude-types): Update via auto-generation.
  167. ;;
  168. ;; Revision 1.19 2005/11/21 20:44:13 monnier
  169. ;; (haskell-doc-extract-types): Get it partly working.
  170. ;; (haskell-doc-fetch-lib-urls): Don't use a literal if we apply
  171. ;; `nreverse' on it later on.
  172. ;; (haskell-doc-prelude-types): Update some parts by auto-generation.
  173. ;; (haskell-doc-grab, haskell-doc-string-nub-ws): Simplify.
  174. ;;
  175. ;; Revision 1.18 2005/11/21 18:02:15 monnier
  176. ;; (haskell-doc-maintainer, haskell-doc-varlist)
  177. ;; (haskell-doc-submit-bug-report, haskell-doc-ftp-site)
  178. ;; (haskell-doc-visit-home): Remove.
  179. ;; (haskell-doc-reserved-ids, haskell-doc-fetch-lib-urls)
  180. ;; (haskell-doc-extract-and-insert-types): New funs.
  181. ;; (haskell-doc-reserved-ids): Fix type of `map'.
  182. ;;
  183. ;; Revision 1.17 2005/11/20 23:55:09 monnier
  184. ;; Add coding cookie.
  185. ;;
  186. ;; Revision 1.16 2005/11/07 01:28:16 monnier
  187. ;; (haskell-doc-xemacs-p, haskell-doc-emacs-p)
  188. ;; (haskell-doc-message): Remove.
  189. ;; (haskell-doc-is-id-char-at): Remove.
  190. ;; (haskell-doc-get-current-word): Rewrite.
  191. ;;
  192. ;; Revision 1.15 2005/11/04 17:11:12 monnier
  193. ;; Add arch-tag.
  194. ;;
  195. ;; Revision 1.14 2005/08/24 11:36:32 monnier
  196. ;; (haskell-doc-message): Paren typo.
  197. ;;
  198. ;; Revision 1.13 2005/08/23 19:23:27 monnier
  199. ;; (haskell-doc-show-type): Assume that the availability
  200. ;; of display-message won't change at runtime.
  201. ;;
  202. ;; Revision 1.12 2005/07/18 21:04:14 monnier
  203. ;; (haskell-doc-message): Remove.
  204. ;; (haskell-doc-show-type): inline it. Do nothing for if there's no doc to show.
  205. ;;
  206. ;; Revision 1.11 2004/12/10 17:33:18 monnier
  207. ;; (haskell-doc-minor-mode-string): Make it dynamic.
  208. ;; (haskell-doc-install-keymap): Remove conflicting C-c C-o binding.
  209. ;; (haskell-doc-mode): Make a nil arg turn the mode ON.
  210. ;; (turn-on-haskell-doc-mode): Make it an alias for haskell-doc-mode.
  211. ;; (haskell-doc-mode): Don't touch haskell-doc-minor-mode-string.
  212. ;; (haskell-doc-show-global-types): Don't touch
  213. ;; haskell-doc-minor-mode-string. Call haskell-doc-make-global-fct-index.
  214. ;; (haskell-doc-check-active): Fix message.
  215. ;; (define-key-after): Don't define.
  216. ;; (haskell-doc-install-keymap): Check existence of define-key-after.
  217. ;;
  218. ;; Revision 1.10 2004/11/25 23:03:23 monnier
  219. ;; (haskell-doc-sym-doc): Make even the last char bold.
  220. ;;
  221. ;; Revision 1.9 2004/11/24 22:14:36 monnier
  222. ;; (haskell-doc-install-keymap): Don't blindly assume there's a Hugs menu.
  223. ;;
  224. ;; Revision 1.8 2004/11/22 10:45:35 simonmar
  225. ;; Fix type of getLine
  226. ;;
  227. ;; Revision 1.7 2004/10/14 22:27:47 monnier
  228. ;; (turn-off-haskell-doc-mode, haskell-doc-current-info): Don't autoload.
  229. ;;
  230. ;; Revision 1.6 2004/10/13 22:45:22 monnier
  231. ;; (haskell-doc): New group.
  232. ;; (haskell-doc-show-reserved, haskell-doc-show-prelude)
  233. ;; (haskell-doc-show-strategy, haskell-doc-show-user-defined)
  234. ;; (haskell-doc-chop-off-context, haskell-doc-chop-off-fctname):
  235. ;; Make them custom vars.
  236. ;; (haskell-doc-keymap): Declare and fill it right there.
  237. ;; (haskell-doc-mode): Simplify.
  238. ;; (haskell-doc-toggle-var): Make it into what it was supposed to be.
  239. ;; (haskell-doc-mode-print-current-symbol-info): Simplify.
  240. ;; (haskell-doc-current-info): New autoloaded function.
  241. ;; (haskell-doc-sym-doc): New fun extracted from haskell-doc-show-type.
  242. ;; (haskell-doc-show-type): Use it.
  243. ;; (haskell-doc-wrapped-type-p): Remove unused var `lim'.
  244. ;; (haskell-doc-forward-sexp-safe, haskell-doc-current-symbol): Remove. Unused.
  245. ;; (haskell-doc-visit-home): Don't require ange-ftp, it's autoloaded.
  246. ;; (haskell-doc-install-keymap): Simplify.
  247. ;;
  248. ;; Revision 1.5 2003/01/09 11:56:26 simonmar
  249. ;; Patches from Ville Skyttä <scop@xemacs.org>, the XEmacs maintainer of
  250. ;; the haskell-mode:
  251. ;;
  252. ;; - Make the auto-mode-alist modifications autoload-only.
  253. ;;
  254. ;; Revision 1.4 2002/10/14 09:55:03 simonmar
  255. ;; Patch to update the Prelude/libraries function names and to remove
  256. ;; support for older versions of Haskell.
  257. ;;
  258. ;; Submitted by: Anders Lau Olsen <alauo@mip.sdu.dk>
  259. ;;
  260. ;; Revision 1.3 2002/04/30 09:34:37 rrt
  261. ;; Remove supporting Haskell 1.4 and 1.2 from the ToDo list. It's Far Too Late.
  262. ;;
  263. ;; Add (require 'imenu). Thanks to N. Y. Kwok.
  264. ;;
  265. ;; Revision 1.2 2002/04/23 14:45:10 simonmar
  266. ;; Tweaks to the doc strings and support for customization, from
  267. ;; Ville Skyttä <scop@xemacs.org>.
  268. ;;
  269. ;; Revision 1.1 2001/07/19 16:17:36 rrt
  270. ;; Add the current version of the Moss/Thorn/Marlow Emacs mode, along with its
  271. ;; web pages and sample files. This is now the preferred mode, and the
  272. ;; haskell.org pages are being changed to reflect that. Also includes the new
  273. ;; GHCi mode from Chris Webb.
  274. ;;
  275. ;; Revision 1.6 1998/12/10 16:27:25 hwloidl
  276. ;; Minor changes ("Doc" as modeline string, mouse-3 moved to C-S-M-mouse-3)
  277. ;;
  278. ;; Revision 1.5 1998/09/24 14:25:46 gem
  279. ;; Fixed minor compatibility bugs with Haskell mode of Moss&Thorn.
  280. ;; Disabled M-/ binding.
  281. ;;
  282. ;; Revision 1.4 1997/11/12 23:51:19 hwloidl
  283. ;; Fixed start-up problem under emacs-19.34.
  284. ;; Added support for wrapped (multi-line) types and 2 vars to control the
  285. ;; behaviour with long fct types
  286. ;;
  287. ;; Revision 1.3 1997/11/03 00:48:03 hwloidl
  288. ;; Major revision for first release.
  289. ;; Added alists for showing prelude fcts, haskell syntax, and strategies
  290. ;; Added mouse interface to show type under mouse
  291. ;; Fixed bug which causes demon to fall over
  292. ;; Works now with hugs-mode and haskell-mode under emacs 19.34,20 and xemacs 19.15
  293. ;;
  294. ;;; Code:
  295. ;; =====
  296. ;;@menu
  297. ;;* Constants and Variables::
  298. ;;* Install as minor mode::
  299. ;;* Menubar Support::
  300. ;;* Haskell Doc Mode::
  301. ;;* Switch it on or off::
  302. ;;* Check::
  303. ;;* Top level function::
  304. ;;* Mouse interface::
  305. ;;* Print fctsym::
  306. ;;* Movement::
  307. ;;* Bug Reports::
  308. ;;* Visit home site::
  309. ;;* Index::
  310. ;;* Token::
  311. ;;@end menu
  312. ;;@node top, Constants and Variables, (dir), (dir)
  313. ;;@top
  314. ;;@node Constants and Variables, Install as minor mode, top, top
  315. ;;@section Constants and Variables
  316. ;;@menu
  317. ;;* Emacs portability::
  318. ;;* Maintenance stuff::
  319. ;;* Mode Variable::
  320. ;;* Variables::
  321. ;;* Prelude types::
  322. ;;* Test membership::
  323. ;;@end menu
  324. ;;@node Emacs portability, Maintenance stuff, Constants and Variables, Constants and Variables
  325. ;;@subsection Emacs portability
  326. (require 'haskell-mode)
  327. (eval-when-compile (require 'cl))
  328. (defgroup haskell-doc nil
  329. "Show Haskell function types in echo area."
  330. :group 'haskell
  331. :prefix "haskell-doc-")
  332. ;;@node Mode Variable, Variables, Maintenance stuff, Constants and Variables
  333. ;;@subsection Mode Variable
  334. (defvar haskell-doc-mode nil
  335. "*If non-nil, show the type of the function near point or a related comment.
  336. If the identifier near point is a Haskell keyword and the variable
  337. `haskell-doc-show-reserved' is non-nil show a one line summary
  338. of the syntax.
  339. If the identifier near point is a Prelude or one of the standard library
  340. functions and `haskell-doc-show-prelude' is non-nil show its type.
  341. If the identifier near point is local \(i.e. defined in this module\) check
  342. the `imenu' list of functions for the type. This obviously requires that
  343. your language mode uses `imenu'.
  344. If the identifier near point is global \(i.e. defined in an imported module\)
  345. and the variable `haskell-doc-show-global-types' is non-nil show the type of its
  346. function.
  347. If the identifier near point is a standard strategy or a function, type related
  348. related to strategies and `haskell-doc-show-strategy' is non-nil show the type
  349. of the function. Strategies are special to the parallel execution of Haskell.
  350. If you're not interested in that just turn it off.
  351. If the identifier near point is a user defined function that occurs as key
  352. in the alist `haskell-doc-user-defined-ids' and the variable
  353. `haskell-doc-show-user-defined' is non-nil show the type of the function.
  354. This variable is buffer-local.")
  355. (make-variable-buffer-local 'haskell-doc-mode)
  356. (defvar haskell-doc-mode-hook nil
  357. "Hook invoked when entering `haskell-doc-mode'.")
  358. (defvar haskell-doc-index nil
  359. "Variable holding an alist matching file names to fct-type alists.
  360. The function `haskell-doc-make-global-fct-index' rebuilds this variables
  361. \(similar to an `imenu' rescan\).
  362. This variable is buffer-local.")
  363. (make-variable-buffer-local 'haskell-doc-index)
  364. (defcustom haskell-doc-show-global-types nil
  365. "If non-nil, search for the types of global functions by loading the files.
  366. This variable is buffer-local."
  367. :group 'haskell-doc
  368. :type 'boolean)
  369. (make-variable-buffer-local 'haskell-doc-show-global-types)
  370. (defcustom haskell-doc-show-reserved t
  371. "If non-nil, show a documentation string for reserved ids.
  372. This variable is buffer-local."
  373. :group 'haskell-doc
  374. :type 'boolean)
  375. (make-variable-buffer-local 'haskell-doc-show-reserved)
  376. (defcustom haskell-doc-show-prelude t
  377. "If non-nil, show a documentation string for prelude functions.
  378. This variable is buffer-local."
  379. :group 'haskell-doc
  380. :type 'boolean)
  381. (make-variable-buffer-local 'haskell-doc-show-prelude)
  382. (defcustom haskell-doc-show-strategy t
  383. "If non-nil, show a documentation string for strategies.
  384. This variable is buffer-local."
  385. :group 'haskell-doc
  386. :type 'boolean)
  387. (make-variable-buffer-local 'haskell-doc-show-strategy)
  388. (defcustom haskell-doc-show-user-defined t
  389. "If non-nil, show a documentation string for user defined ids.
  390. This variable is buffer-local."
  391. :group 'haskell-doc
  392. :type 'boolean)
  393. (make-variable-buffer-local 'haskell-doc-show-user-defined)
  394. (defcustom haskell-doc-chop-off-context t
  395. "If non-nil eliminate the context part in a Haskell type."
  396. :group 'haskell-doc
  397. :type 'boolean)
  398. (defcustom haskell-doc-chop-off-fctname nil
  399. "If non-nil omit the function name and show only the type."
  400. :group 'haskell-doc
  401. :type 'boolean)
  402. (defvar haskell-doc-search-distance 40 ; distance in characters
  403. "*How far to search when looking for the type declaration of fct under cursor.")
  404. ;;@node Variables, Prelude types, Mode Variable, Constants and Variables
  405. ;;@subsection Variables
  406. (defvar haskell-doc-idle-delay 0.50
  407. "*Number of seconds of idle time to wait before printing.
  408. If user input arrives before this interval of time has elapsed after the
  409. last input, no documentation will be printed.
  410. If this variable is set to 0, no idle time is required.")
  411. (defvar haskell-doc-argument-case 'identity ; 'upcase
  412. "Case to display argument names of functions, as a symbol.
  413. This has two preferred values: `upcase' or `downcase'.
  414. Actually, any name of a function which takes a string as an argument and
  415. returns another string is acceptable.")
  416. (defvar haskell-doc-mode-message-commands nil
  417. "*Obarray of command names where it is appropriate to print in the echo area.
  418. This is not done for all commands since some print their own
  419. messages in the echo area, and these functions would instantly overwrite
  420. them. But `self-insert-command' as well as most motion commands are good
  421. candidates.
  422. It is probably best to manipulate this data structure with the commands
  423. `haskell-doc-add-command' and `haskell-doc-remove-command'.")
  424. ;;(cond ((null haskell-doc-mode-message-commands)
  425. ;; ;; If you increase the number of buckets, keep it a prime number.
  426. ;; (setq haskell-doc-mode-message-commands (make-vector 31 0))
  427. ;; (let ((list '("self-insert-command"
  428. ;; "next-" "previous-"
  429. ;; "forward-" "backward-"
  430. ;; "beginning-of-" "end-of-"
  431. ;; "goto-"
  432. ;; "recenter"
  433. ;; "scroll-"))
  434. ;; (syms nil))
  435. ;; (while list
  436. ;; (setq syms (all-completions (car list) obarray 'fboundp))
  437. ;; (setq list (cdr list))
  438. ;; (while syms
  439. ;; (set (intern (car syms) haskell-doc-mode-message-commands) t)
  440. ;; (setq syms (cdr syms)))))))
  441. ;; Bookkeeping; the car contains the last symbol read from the buffer.
  442. ;; The cdr contains the string last displayed in the echo area, so it can
  443. ;; be printed again if necessary without reconsing.
  444. (defvar haskell-doc-last-data '(nil . nil))
  445. (defvar haskell-doc-minor-mode-string
  446. '(haskell-doc-show-global-types " DOC" " Doc")
  447. "*String to display in mode line when Haskell-Doc Mode is enabled.")
  448. ;;@node Prelude types, Test membership, Variables, Constants and Variables
  449. ;;@subsection Prelude types
  450. ;;@cindex haskell-doc-reserved-ids
  451. (defvar haskell-doc-reserved-ids
  452. '(("case" . "case exp of { alts [;] }")
  453. ("class" . "class [context =>] simpleclass [where { cbody [;] }]")
  454. ("data" . "data [context =>] simpletype = constrs [deriving]")
  455. ("default" . "default (type1 , ... , typen)")
  456. ("deriving" . "deriving (dclass | (dclass1, ... , dclassn))") ; used with data or newtype
  457. ("do" . "do { stmts [;] } stmts -> exp [; stmts] | pat <- exp ; stmts | let decllist ; stmts")
  458. ("else" . "if exp then exp else exp")
  459. ("if" . "if exp then exp else exp")
  460. ("import" . "import [qualified] modid [as modid] [impspec]")
  461. ("in" . "let decllist in exp")
  462. ("infix" . "infix [digit] ops")
  463. ("infixl" . "infixl [digit] ops")
  464. ("infixr" . "infixr [digit] ops")
  465. ("instance" . "instance [context =>] qtycls inst [where { valdefs [;] }]")
  466. ("let" . "let { decl; ...; decl [;] } in exp")
  467. ("module" . "module modid [exports] where body")
  468. ("newtype" . "newtype [context =>] simpletype = con atype [deriving]")
  469. ("of" . "case exp of { alts [;] }")
  470. ("then" . "if exp then exp else exp")
  471. ("type" . "type simpletype = type")
  472. ("where" . "exp where { decl; ...; decl [;] }") ; check that ; see also class, instance, module
  473. ("as" . "import [qualified] modid [as modid] [impspec]")
  474. ("qualified" . "import [qualified] modid [as modid] [impspec]")
  475. ("hiding" . "hiding ( import1 , ... , importn [ , ] )"))
  476. "An alist of reserved identifiers.
  477. Each element is of the form (ID . DOC) where both ID and DOC are strings.
  478. DOC should be a concise single-line string describing the construct in which
  479. the keyword is used.")
  480. (eval-and-compile
  481. (defalias 'haskell-doc-split-string
  482. (if (condition-case ()
  483. (split-string "" nil t)
  484. (wrong-number-of-arguments nil))
  485. 'split-string
  486. ;; copied from Emacs 22
  487. (lambda (string &optional separators omit-nulls)
  488. (let ((keep-nulls (not (if separators omit-nulls t)))
  489. (rexp (or separators "[ \f\t\n\r\v]+"))
  490. (start 0)
  491. notfirst
  492. (list nil))
  493. (while (and (string-match rexp string
  494. (if (and notfirst
  495. (= start (match-beginning 0))
  496. (< start (length string)))
  497. (1+ start) start))
  498. (< start (length string)))
  499. (setq notfirst t)
  500. (if (or keep-nulls (< start (match-beginning 0)))
  501. (setq list
  502. (cons (substring string start (match-beginning 0))
  503. list)))
  504. (setq start (match-end 0)))
  505. (if (or keep-nulls (< start (length string)))
  506. (setq list
  507. (cons (substring string start)
  508. list)))
  509. (nreverse list))))))
  510. ;;@cindex haskell-doc-prelude-types
  511. (defun haskell-doc-extract-types (url)
  512. (with-temp-buffer
  513. (insert-file-contents url)
  514. (goto-char (point-min))
  515. (while (search-forward "&nbsp;" nil t) (replace-match " " t t))
  516. ;; First, focus on the actual code, removing the surrounding HTML text.
  517. (goto-char (point-min))
  518. (let ((last (point-min))
  519. (modules nil))
  520. (while (re-search-forward "^module +\\([[:alnum:]]+\\)" nil t)
  521. (let ((module (match-string 1)))
  522. (if (member module modules)
  523. ;; The library nodes of the HTML doc contain modules twice:
  524. ;; once at the top, with only type declarations, and once at
  525. ;; the bottom with an actual sample implementation which may
  526. ;; include declaration of non-exported values.
  527. ;; We're now at this second occurrence is the implementation
  528. ;; which should thus be ignored.
  529. nil
  530. (push module modules)
  531. (delete-region last (point))
  532. (search-forward "</tt>")
  533. ;; Some of the blocks of code are split.
  534. (while (looking-at "\\(<[^<>]+>[ \t\n]*\\)*<tt>")
  535. (goto-char (match-end 0))
  536. (search-forward "</tt>"))
  537. (setq last (point)))))
  538. (delete-region last (point-max))
  539. ;; Then process the HTML encoding to get back to pure ASCII.
  540. (goto-char (point-min))
  541. (while (search-forward "<br>" nil t) (replace-match "\n" t t))
  542. ;; (goto-char (point-min))
  543. ;; (while (re-search-forward "<[^<>]+>" nil t) (replace-match "" t t))
  544. (goto-char (point-min))
  545. (while (search-forward "&gt;" nil t) (replace-match ">" t t))
  546. (goto-char (point-min))
  547. (while (search-forward "&lt;" nil t) (replace-match "<" t t))
  548. (goto-char (point-min))
  549. (while (search-forward "&amp;" nil t) (replace-match "&" t t))
  550. (goto-char (point-min))
  551. (if (re-search-forward "&[a-z]+;" nil t)
  552. (error "Unexpected charref %s" (match-string 0)))
  553. ;; Remove TABS.
  554. (goto-char (point-min))
  555. (while (search-forward "\t" nil t) (replace-match " " t t))
  556. ;; Finally, extract the actual data.
  557. (goto-char (point-min))
  558. (let* ((elems nil)
  559. (space-re "[ \t\n]*\\(?:--.*\n[ \t\n]*\\)*")
  560. (comma-re (concat " *," space-re))
  561. ;; A list of identifiers. We have to be careful to weed out
  562. ;; entries like "ratPrec = 7 :: Int". Also ignore entries
  563. ;; which start with a < since they're actually in the HTML text
  564. ;; part. And the list may be spread over several lines, cut
  565. ;; after a comma.
  566. (idlist-re
  567. (concat "\\([^< \t\n][^ \t\n]*"
  568. "\\(?:" comma-re "[^ \t\n]+\\)*\\)"))
  569. ;; A type. A few types are spread over 2 lines,
  570. ;; cut after the "=>", so we have to handle these as well.
  571. (type-re "\\(.*[^\n>]\\(?:>[ \t\n]+.*[^\n>]\\)*\\) *$")
  572. ;; A decl of a list of values, possibly indented.
  573. (val-decl-re
  574. (concat "^\\( +\\)?" idlist-re "[ \t\n]*::[ \t\n]*" type-re))
  575. (re (concat
  576. ;; 3 possibilities: a class decl, a data decl, or val decl.
  577. ;; First, let's match a class decl.
  578. "^class \\(?:.*=>\\)? *\\(.*[^ \t\n]\\)[ \t\n]*where"
  579. ;; Or a value decl:
  580. "\\|" val-decl-re
  581. "\\|" ;; Or a data decl. We only handle single-arm
  582. ;; datatypes with labels.
  583. "^data +\\([[:alnum:]][[:alnum:] ]*[[:alnum:]]\\)"
  584. " *=.*{\\([^}]+\\)}"
  585. ))
  586. (re-class (concat "^[^ \t\n]\\|" re))
  587. curclass)
  588. (while (re-search-forward (if curclass re-class re) nil t)
  589. (cond
  590. ;; A class decl.
  591. ((match-end 1) (setq curclass (match-string 1)))
  592. ;; A value decl.
  593. ((match-end 4)
  594. (let ((type (match-string 4))
  595. (vars (match-string 3))
  596. (indented (match-end 2)))
  597. (if (string-match "[ \t\n][ \t\n]+" type)
  598. (setq type (replace-match " " t t type)))
  599. (if (string-match " *\\(--.*\\)?\\'" type)
  600. (setq type (substring type 0 (match-beginning 0))))
  601. (if indented
  602. (if curclass
  603. (if (string-match "\\`\\(.*[^ \t\n]\\) *=> *" type)
  604. (let ((classes (match-string 1 type)))
  605. (setq type (substring type (match-end 0)))
  606. (if (string-match "\\`(.*)\\'" classes)
  607. (setq classes (substring classes 1 -1)))
  608. (setq type (concat "(" curclass ", " classes
  609. ") => " type)))
  610. (setq type (concat curclass " => " type)))
  611. ;; It's actually not an error: just a type annotation on
  612. ;; some local variable.
  613. ;; (error "Indentation outside a class in %s: %s"
  614. ;; module vars)
  615. nil)
  616. (setq curclass nil))
  617. (dolist (var (haskell-doc-split-string vars comma-re t))
  618. (if (string-match "(.*)" var) (setq var (substring var 1 -1)))
  619. (push (cons var type) elems))))
  620. ;; A datatype decl.
  621. ((match-end 5)
  622. (setq curclass nil)
  623. (let ((name (match-string 5)))
  624. (save-excursion
  625. (save-restriction
  626. (narrow-to-region (match-beginning 6) (match-end 6))
  627. (goto-char (point-min))
  628. (while (re-search-forward val-decl-re nil t)
  629. (let ((vars (match-string 2))
  630. (type (match-string 3)))
  631. (if (string-match "[ \t\n][ \t\n]+" type)
  632. (setq type (replace-match " " t t type)))
  633. (if (string-match " *\\(--.*\\)?\\'" type)
  634. (setq type (substring type 0 (match-beginning 0))))
  635. (if (string-match ",\\'" type)
  636. (setq type (substring type 0 -1)))
  637. (setq type (concat name " -> " type))
  638. (dolist (var (haskell-doc-split-string vars comma-re t))
  639. (if (string-match "(.*)" var)
  640. (setq var (substring var 1 -1)))
  641. (push (cons var type) elems))))))))
  642. ;; The end of a class declaration.
  643. (t (setq curclass nil) (beginning-of-line))))
  644. (cons (car (last modules)) elems)))))
  645. (defun haskell-doc-fetch-lib-urls (base-url)
  646. (with-temp-buffer
  647. (insert-file-contents base-url)
  648. (goto-char (point-min))
  649. (search-forward "Part II: Libraries")
  650. (delete-region (point-min) (point))
  651. (search-forward "</table>")
  652. (delete-region (point) (point-max))
  653. (goto-char (point-min))
  654. (let ((libs (list "standard-prelude.html")))
  655. (while (re-search-forward "<a href=\"\\([^\"]+\\)\">" nil t)
  656. (push (match-string 1) libs))
  657. (mapcar (lambda (s) (expand-file-name s (file-name-directory base-url)))
  658. (nreverse libs)))))
  659. (defun haskell-doc-extract-and-insert-types (url)
  660. "Fetch the types from the online doc and insert them at point.
  661. URL is the URL of the online doc."
  662. (interactive (if current-prefix-arg
  663. (read-file-name "URL: ")
  664. (list "http://www.haskell.org/onlinereport/")))
  665. (let ((urls (haskell-doc-fetch-lib-urls url)))
  666. (dolist (url urls)
  667. (let ((data (haskell-doc-extract-types url)))
  668. (insert ";; " (pop data)) (indent-according-to-mode) (newline)
  669. (dolist (elem (sort data (lambda (x y) (string-lessp (car x) (car y)))))
  670. (prin1 elem (current-buffer))
  671. (indent-according-to-mode) (newline))))))
  672. (defvar haskell-doc-prelude-types
  673. ;; This list was auto generated by `haskell-doc-extract-and-insert-types'.
  674. '(
  675. ;; Prelude
  676. ("!!" . "[a] -> Int -> a")
  677. ("$" . "(a -> b) -> a -> b")
  678. ("$!" . "(a -> b) -> a -> b")
  679. ("&&" . "Bool -> Bool -> Bool")
  680. ("*" . "Num a => a -> a -> a")
  681. ("**" . "Floating a => a -> a -> a")
  682. ("+" . "Num a => a -> a -> a")
  683. ("++" . "[a] -> [a] -> [a]")
  684. ("-" . "Num a => a -> a -> a")
  685. ("." . "(b -> c) -> (a -> b) -> a -> c")
  686. ("/" . "Fractional a => a -> a -> a")
  687. ("/=" . "Eq a => a -> a -> Bool")
  688. ("<" . "Ord a => a -> a -> Bool")
  689. ("<=" . "Ord a => a -> a -> Bool")
  690. ("=<<" . "Monad m => (a -> m b) -> m a -> m b")
  691. ("==" . "Eq a => a -> a -> Bool")
  692. (">" . "Ord a => a -> a -> Bool")
  693. (">=" . "Ord a => a -> a -> Bool")
  694. (">>" . "Monad m => m a -> m b -> m b")
  695. (">>=" . "Monad m => m a -> (a -> m b) -> m b")
  696. ("^" . "(Num a, Integral b) => a -> b -> a")
  697. ("^^" . "(Fractional a, Integral b) => a -> b -> a")
  698. ("abs" . "Num a => a -> a")
  699. ("acos" . "Floating a => a -> a")
  700. ("acosh" . "Floating a => a -> a")
  701. ("all" . "(a -> Bool) -> [a] -> Bool")
  702. ("and" . "[Bool] -> Bool")
  703. ("any" . "(a -> Bool) -> [a] -> Bool")
  704. ("appendFile" . "FilePath -> String -> IO ()")
  705. ("asTypeOf" . "a -> a -> a")
  706. ("asin" . "Floating a => a -> a")
  707. ("asinh" . "Floating a => a -> a")
  708. ("atan" . "Floating a => a -> a")
  709. ("atan2" . "RealFloat a => a -> a -> a")
  710. ("atanh" . "Floating a => a -> a")
  711. ("break" . "(a -> Bool) -> [a] -> ([a],[a])")
  712. ("catch" . "IO a -> (IOError -> IO a) -> IO a")
  713. ("ceiling" . "(RealFrac a, Integral b) => a -> b")
  714. ("compare" . "Ord a => a -> a -> Ordering")
  715. ("concat" . "[[a]] -> [a]")
  716. ("concatMap" . "(a -> [b]) -> [a] -> [b]")
  717. ("const" . "a -> b -> a")
  718. ("cos" . "Floating a => a -> a")
  719. ("cosh" . "Floating a => a -> a")
  720. ("curry" . "((a, b) -> c) -> a -> b -> c")
  721. ("cycle" . "[a] -> [a]")
  722. ("decodeFloat" . "RealFloat a => a -> (Integer,Int)")
  723. ("div" . "Integral a => a -> a -> a")
  724. ("divMod" . "Integral a => a -> a -> (a,a)")
  725. ("drop" . "Int -> [a] -> [a]")
  726. ("dropWhile" . "(a -> Bool) -> [a] -> [a]")
  727. ("either" . "(a -> c) -> (b -> c) -> Either a b -> c")
  728. ("elem" . "(Eq a) => a -> [a] -> Bool")
  729. ("encodeFloat" . "RealFloat a => Integer -> Int -> a")
  730. ("enumFrom" . "Enum a => a -> [a]")
  731. ("enumFromThen" . "Enum a => a -> a -> [a]")
  732. ("enumFromThenTo" . "Enum a => a -> a -> a -> [a]")
  733. ("enumFromTo" . "Enum a => a -> a -> [a]")
  734. ("error" . "String -> a")
  735. ("even" . "(Integral a) => a -> Bool")
  736. ("exp" . "Floating a => a -> a")
  737. ("exponent" . "RealFloat a => a -> Int")
  738. ("fail" . "Monad m => String -> m a")
  739. ("filter" . "(a -> Bool) -> [a] -> [a]")
  740. ("flip" . "(a -> b -> c) -> b -> a -> c")
  741. ("floatDigits" . "RealFloat a => a -> Int")
  742. ("floatRadix" . "RealFloat a => a -> Integer")
  743. ("floatRange" . "RealFloat a => a -> (Int,Int)")
  744. ("floor" . "(RealFrac a, Integral b) => a -> b")
  745. ("fmap" . "Functor f => (a -> b) -> f a -> f b")
  746. ("foldl" . "(a -> b -> a) -> a -> [b] -> a")
  747. ("foldl1" . "(a -> a -> a) -> [a] -> a")
  748. ("foldr" . "(a -> b -> b) -> b -> [a] -> b")
  749. ("foldr1" . "(a -> a -> a) -> [a] -> a")
  750. ("fromEnum" . "Enum a => a -> Int")
  751. ("fromInteger" . "Num a => Integer -> a")
  752. ("fromIntegral" . "(Integral a, Num b) => a -> b")
  753. ("fromRational" . "Fractional a => Rational -> a")
  754. ("fst" . "(a,b) -> a")
  755. ("gcd" . "(Integral a) => a -> a -> a")
  756. ("getChar" . "IO Char")
  757. ("getContents" . "IO String")
  758. ("getLine" . "IO String")
  759. ("head" . "[a] -> a")
  760. ("id" . "a -> a")
  761. ("init" . "[a] -> [a]")
  762. ("interact" . "(String -> String) -> IO ()")
  763. ("ioError" . "IOError -> IO a")
  764. ("isDenormalized" . "RealFloat a => a -> Bool")
  765. ("isIEEE" . "RealFloat a => a -> Bool")
  766. ("isInfinite" . "RealFloat a => a -> Bool")
  767. ("isNaN" . "RealFloat a => a -> Bool")
  768. ("isNegativeZero" . "RealFloat a => a -> Bool")
  769. ("iterate" . "(a -> a) -> a -> [a]")
  770. ("last" . "[a] -> a")
  771. ("lcm" . "(Integral a) => a -> a -> a")
  772. ("length" . "[a] -> Int")
  773. ("lex" . "ReadS String")
  774. ("lines" . "String -> [String]")
  775. ("log" . "Floating a => a -> a")
  776. ("logBase" . "Floating a => a -> a -> a")
  777. ("lookup" . "(Eq a) => a -> [(a,b)] -> Maybe b")
  778. ("map" . "(a -> b) -> [a] -> [b]")
  779. ("mapM" . "Monad m => (a -> m b) -> [a] -> m [b]")
  780. ("mapM_" . "Monad m => (a -> m b) -> [a] -> m ()")
  781. ("max" . "Ord a => a -> a -> a")
  782. ("maxBound" . "Bounded a => a")
  783. ("maximum" . "(Ord a) => [a] -> a")
  784. ("maybe" . "b -> (a -> b) -> Maybe a -> b")
  785. ("min" . "Ord a => a -> a -> a")
  786. ("minBound" . "Bounded a => a")
  787. ("minimum" . "(Ord a) => [a] -> a")
  788. ("mod" . "Integral a => a -> a -> a")
  789. ("negate" . "Num a => a -> a")
  790. ("not" . "Bool -> Bool")
  791. ("notElem" . "(Eq a) => a -> [a] -> Bool")
  792. ("null" . "[a] -> Bool")
  793. ("numericEnumFrom" . "(Fractional a) => a -> [a]")
  794. ("numericEnumFromThen" . "(Fractional a) => a -> a -> [a]")
  795. ("numericEnumFromThenTo" . "(Fractional a, Ord a) => a -> a -> a -> [a]")
  796. ("numericEnumFromTo" . "(Fractional a, Ord a) => a -> a -> [a]")
  797. ("odd" . "(Integral a) => a -> Bool")
  798. ("or" . "[Bool] -> Bool")
  799. ("otherwise" . "Bool")
  800. ("pi" . "Floating a => a")
  801. ("pred" . "Enum a => a -> a")
  802. ("print" . "Show a => a -> IO ()")
  803. ("product" . "(Num a) => [a] -> a")
  804. ("properFraction" . "(RealFrac a, Integral b) => a -> (b,a)")
  805. ("putChar" . "Char -> IO ()")
  806. ("putStr" . "String -> IO ()")
  807. ("putStrLn" . "String -> IO ()")
  808. ("quot" . "Integral a => a -> a -> a")
  809. ("quotRem" . "Integral a => a -> a -> (a,a)")
  810. ("read" . "(Read a) => String -> a")
  811. ("readFile" . "FilePath -> IO String")
  812. ("readIO" . "Read a => String -> IO a")
  813. ("readList" . "Read a => ReadS [a]")
  814. ("readLn" . "Read a => IO a")
  815. ("readParen" . "Bool -> ReadS a -> ReadS a")
  816. ("reads" . "(Read a) => ReadS a")
  817. ("readsPrec" . "Read a => Int -> ReadS a")
  818. ("realToFrac" . "(Real a, Fractional b) => a -> b")
  819. ("recip" . "Fractional a => a -> a")
  820. ("rem" . "Integral a => a -> a -> a")
  821. ("repeat" . "a -> [a]")
  822. ("replicate" . "Int -> a -> [a]")
  823. ("return" . "Monad m => a -> m a")
  824. ("reverse" . "[a] -> [a]")
  825. ("round" . "(RealFrac a, Integral b) => a -> b")
  826. ("scaleFloat" . "RealFloat a => Int -> a -> a")
  827. ("scanl" . "(a -> b -> a) -> a -> [b] -> [a]")
  828. ("scanl1" . "(a -> a -> a) -> [a] -> [a]")
  829. ("scanr" . "(a -> b -> b) -> b -> [a] -> [b]")
  830. ("scanr1" . "(a -> a -> a) -> [a] -> [a]")
  831. ("seq" . "a -> b -> b")
  832. ("sequence" . "Monad m => [m a] -> m [a]")
  833. ("sequence_" . "Monad m => [m a] -> m ()")
  834. ("show" . "Show a => a -> String")
  835. ("showChar" . "Char -> ShowS")
  836. ("showList" . "Show a => [a] -> ShowS")
  837. ("showParen" . "Bool -> ShowS -> ShowS")
  838. ("showString" . "String -> ShowS")
  839. ("shows" . "(Show a) => a -> ShowS")
  840. ("showsPrec" . "Show a => Int -> a -> ShowS")
  841. ("significand" . "RealFloat a => a -> a")
  842. ("signum" . "Num a => a -> a")
  843. ("sin" . "Floating a => a -> a")
  844. ("sinh" . "Floating a => a -> a")
  845. ("snd" . "(a,b) -> b")
  846. ("span" . "(a -> Bool) -> [a] -> ([a],[a])")
  847. ("splitAt" . "Int -> [a] -> ([a],[a])")
  848. ("sqrt" . "Floating a => a -> a")
  849. ("subtract" . "(Num a) => a -> a -> a")
  850. ("succ" . "Enum a => a -> a")
  851. ("sum" . "(Num a) => [a] -> a")
  852. ("tail" . "[a] -> [a]")
  853. ("take" . "Int -> [a] -> [a]")
  854. ("takeWhile" . "(a -> Bool) -> [a] -> [a]")
  855. ("tan" . "Floating a => a -> a")
  856. ("tanh" . "Floating a => a -> a")
  857. ("toEnum" . "Enum a => Int -> a")
  858. ("toInteger" . "Integral a => a -> Integer")
  859. ("toRational" . "Real a => a -> Rational")
  860. ("truncate" . "(RealFrac a, Integral b) => a -> b")
  861. ("uncurry" . "(a -> b -> c) -> ((a, b) -> c)")
  862. ("undefined" . "a")
  863. ("unlines" . "[String] -> String")
  864. ("until" . "(a -> Bool) -> (a -> a) -> a -> a")
  865. ("unwords" . "[String] -> String")
  866. ("unzip" . "[(a,b)] -> ([a],[b])")
  867. ("unzip3" . "[(a,b,c)] -> ([a],[b],[c])")
  868. ("userError" . "String -> IOError")
  869. ("words" . "String -> [String]")
  870. ("writeFile" . "FilePath -> String -> IO ()")
  871. ("zip" . "[a] -> [b] -> [(a,b)]")
  872. ("zip3" . "[a] -> [b] -> [c] -> [(a,b,c)]")
  873. ("zipWith" . "(a->b->c) -> [a]->[b]->[c]")
  874. ("zipWith3" . "(a->b->c->d) -> [a]->[b]->[c]->[d]")
  875. ("||" . "Bool -> Bool -> Bool")
  876. ;; Ratio
  877. ("%" . "(Integral a) => a -> a -> Ratio a")
  878. ("approxRational" . "(RealFrac a) => a -> a -> Rational")
  879. ("denominator" . "(Integral a) => Ratio a -> a")
  880. ("numerator" . "(Integral a) => Ratio a -> a")
  881. ;; Complex
  882. ("cis" . "(RealFloat a) => a -> Complex a")
  883. ("conjugate" . "(RealFloat a) => Complex a -> Complex a")
  884. ("imagPart" . "(RealFloat a) => Complex a -> a")
  885. ("magnitude" . "(RealFloat a) => Complex a -> a")
  886. ("mkPolar" . "(RealFloat a) => a -> a -> Complex a")
  887. ("phase" . "(RealFloat a) => Complex a -> a")
  888. ("polar" . "(RealFloat a) => Complex a -> (a,a)")
  889. ("realPart" . "(RealFloat a) => Complex a -> a")
  890. ;; Numeric
  891. ("floatToDigits" . "(RealFloat a) => Integer -> a -> ([Int], Int)")
  892. ("fromRat" . "(RealFloat a) => Rational -> a")
  893. ("lexDigits" . "ReadS String")
  894. ("readDec" . "(Integral a) => ReadS a")
  895. ("readFloat" . "(RealFrac a) => ReadS a")
  896. ("readHex" . "(Integral a) => ReadS a")
  897. ("readInt" . "(Integral a) => a -> (Char -> Bool) -> (Char -> Int) -> ReadS a")
  898. ("readOct" . "(Integral a) => ReadS a")
  899. ("readSigned" . "(Real a) => ReadS a -> ReadS a")
  900. ("showEFloat" . "(RealFloat a) => Maybe Int -> a -> ShowS")
  901. ("showFFloat" . "(RealFloat a) => Maybe Int -> a -> ShowS")
  902. ("showFloat" . "(RealFloat a) => a -> ShowS")
  903. ("showGFloat" . "(RealFloat a) => Maybe Int -> a -> ShowS")
  904. ("showHex" . "Integral a => a -> ShowS")
  905. ("showInt" . "Integral a => a -> ShowS")
  906. ("showIntAtBase" . "Integral a => a -> (Int -> Char) -> a -> ShowS")
  907. ("showOct" . "Integral a => a -> ShowS")
  908. ("showSigned" . "(Real a) => (a -> ShowS) -> Int -> a -> ShowS")
  909. ;; Ix
  910. ("inRange" . "Ix a => (a,a) -> a -> Bool")
  911. ("index" . "Ix a => (a,a) -> a -> Int")
  912. ("range" . "Ix a => (a,a) -> [a]")
  913. ("rangeSize" . "Ix a => (a,a) -> Int")
  914. ;; Array
  915. ("!" . "(Ix a) => Array a b -> a -> b")
  916. ("//" . "(Ix a) => Array a b -> [(a,b)] -> Array a b")
  917. ("accum" . "(Ix a) => (b -> c -> b) -> Array a b -> [(a,c)]")
  918. ("accumArray" . "(Ix a) => (b -> c -> b) -> b -> (a,a) -> [(a,c)]")
  919. ("array" . "(Ix a) => (a,a) -> [(a,b)] -> Array a b")
  920. ("assocs" . "(Ix a) => Array a b -> [(a,b)]")
  921. ("bounds" . "(Ix a) => Array a b -> (a,a)")
  922. ("elems" . "(Ix a) => Array a b -> [b]")
  923. ("indices" . "(Ix a) => Array a b -> [a]")
  924. ("ixmap" . "(Ix a, Ix b) => (a,a) -> (a -> b) -> Array b c")
  925. ("listArray" . "(Ix a) => (a,a) -> [b] -> Array a b")
  926. ;; List
  927. ("\\\\" . "Eq a => [a] -> [a] -> [a]")
  928. ("delete" . "Eq a => a -> [a] -> [a]")
  929. ("deleteBy" . "(a -> a -> Bool) -> a -> [a] -> [a]")
  930. ("deleteFirstsBy" . "(a -> a -> Bool) -> [a] -> [a] -> [a]")
  931. ("elemIndex" . "Eq a => a -> [a] -> Maybe Int")
  932. ("elemIndices" . "Eq a => a -> [a] -> [Int]")
  933. ("find" . "(a -> Bool) -> [a] -> Maybe a")
  934. ("findIndex" . "(a -> Bool) -> [a] -> Maybe Int")
  935. ("findIndices" . "(a -> Bool) -> [a] -> [Int]")
  936. ("genericDrop" . "Integral a => a -> [b] -> [b]")
  937. ("genericIndex" . "Integral a => [b] -> a -> b")
  938. ("genericLength" . "Integral a => [b] -> a")
  939. ("genericReplicate" . "Integral a => a -> b -> [b]")
  940. ("genericSplitAt" . "Integral a => a -> [b] -> ([b],[b])")
  941. ("genericTake" . "Integral a => a -> [b] -> [b]")
  942. ("group" . "Eq a => [a] -> [[a]]")
  943. ("groupBy" . "(a -> a -> Bool) -> [a] -> [[a]]")
  944. ("inits" . "[a] -> [[a]]")
  945. ("insert" . "Ord a => a -> [a] -> [a]")
  946. ("insertBy" . "(a -> a -> Ordering) -> a -> [a] -> [a]")
  947. ("intersect" . "Eq a => [a] -> [a] -> [a]")
  948. ("intersectBy" . "(a -> a -> Bool) -> [a] -> [a] -> [a]")
  949. ("intersperse" . "a -> [a] -> [a]")
  950. ("isPrefixOf" . "Eq a => [a] -> [a] -> Bool")
  951. ("isSuffixOf" . "Eq a => [a] -> [a] -> Bool")
  952. ("mapAccumL" . "(a -> b -> (a, c)) -> a -> [b] -> (a, [c])")
  953. ("mapAccumR" . "(a -> b -> (a, c)) -> a -> [b] -> (a, [c])")
  954. ("maximumBy" . "(a -> a -> Ordering) -> [a] -> a")
  955. ("minimumBy" . "(a -> a -> Ordering) -> [a] -> a")
  956. ("nub" . "Eq a => [a] -> [a]")
  957. ("nubBy" . "(a -> a -> Bool) -> [a] -> [a]")
  958. ("partition" . "(a -> Bool) -> [a] -> ([a],[a])")
  959. ("sort" . "Ord a => [a] -> [a]")
  960. ("sortBy" . "(a -> a -> Ordering) -> [a] -> [a]")
  961. ("tails" . "[a] -> [[a]]")
  962. ("transpose" . "[[a]] -> [[a]]")
  963. ("unfoldr" . "(b -> Maybe (a,b)) -> b -> [a]")
  964. ("union" . "Eq a => [a] -> [a] -> [a]")
  965. ("unionBy" . "(a -> a -> Bool) -> [a] -> [a] -> [a]")
  966. ("unzip4" . "[(a,b,c,d)] -> ([a],[b],[c],[d])")
  967. ("unzip5" . "[(a,b,c,d,e)] -> ([a],[b],[c],[d],[e])")
  968. ("unzip6" . "[(a,b,c,d,e,f)] -> ([a],[b],[c],[d],[e],[f])")
  969. ("unzip7" . "[(a,b,c,d,e,f,g)] -> ([a],[b],[c],[d],[e],[f],[g])")
  970. ("zip4" . "[a] -> [b] -> [c] -> [d] -> [(a,b,c,d)]")
  971. ("zip5" . "[a] -> [b] -> [c] -> [d] -> [e] -> [(a,b,c,d,e)]")
  972. ("zip6" . "[a] -> [b] -> [c] -> [d] -> [e] -> [f]")
  973. ("zip7" . "[a] -> [b] -> [c] -> [d] -> [e] -> [f] -> [g]")
  974. ("zipWith4" . "(a->b->c->d->e) -> [a]->[b]->[c]->[d]->[e]")
  975. ("zipWith5" . "(a->b->c->d->e->f) ->")
  976. ("zipWith6" . "(a->b->c->d->e->f->g) -> [a]->[b]->[c]->[d]->[e]->[f]->[g]")
  977. ("zipWith7" . "(a->b->c->d->e->f->g->h) -> [a]->[b]->[c]->[d]->[e]->[f]->[g]->[h]")
  978. ;; Maybe
  979. ("catMaybes" . "[Maybe a] -> [a]")
  980. ("fromJust" . "Maybe a -> a")
  981. ("fromMaybe" . "a -> Maybe a -> a")
  982. ("isJust" . "Maybe a -> Bool")
  983. ("isNothing" . "Maybe a -> Bool")
  984. ("listToMaybe" . "[a] -> Maybe a")
  985. ("mapMaybe" . "(a -> Maybe b) -> [a] -> [b]")
  986. ("maybeToList" . "Maybe a -> [a]")
  987. ;; Char
  988. ("chr" . "Int -> Char")
  989. ("digitToInt" . "Char -> Int")
  990. ("intToDigit" . "Int -> Char")
  991. ("isAlpha" . "Char -> Bool")
  992. ("isAlphaNum" . "Char -> Bool")
  993. ("isAscii" . "Char -> Bool")
  994. ("isControl" . "Char -> Bool")
  995. ("isDigit" . "Char -> Bool")
  996. ("isHexDigit" . "Char -> Bool")
  997. ("isLatin1" . "Char -> Bool")
  998. ("isLower" . "Char -> Bool")
  999. ("isOctDigit" . "Char -> Bool")
  1000. ("isPrint" . "Char -> Bool")
  1001. ("isSpace" . "Char -> Bool")
  1002. ("isUpper" . "Char -> Bool")
  1003. ("lexLitChar" . "ReadS String")
  1004. ("ord" . "Char -> Int")
  1005. ("readLitChar" . "ReadS Char")
  1006. ("showLitChar" . "Char -> ShowS")
  1007. ("toLower" . "Char -> Char")
  1008. ("toUpper" . "Char -> Char")
  1009. ;; Monad
  1010. ("ap" . "Monad m => m (a -> b) -> m a -> m b")
  1011. ("filterM" . "Monad m => (a -> m Bool) -> [a] -> m [a]")
  1012. ("foldM" . "Monad m => (a -> b -> m a) -> a -> [b] -> m a")
  1013. ("guard" . "MonadPlus m => Bool -> m ()")
  1014. ("join" . "Monad m => m (m a) -> m a")
  1015. ("liftM" . "Monad m => (a -> b) -> (m a -> m b)")
  1016. ("liftM2" . "Monad m => (a -> b -> c) -> (m a -> m b -> m c)")
  1017. ("liftM3" . "Monad m => (a -> b -> c -> d) -> (m a -> m b -> m c -> m d)")
  1018. ("liftM4" . "Monad m => (a -> b -> c -> d -> e) -> (m a -> m b -> m c -> m d -> m e)")
  1019. ("liftM5" . "Monad m => (a -> b -> c -> d -> e -> f) -> (m a -> m b -> m c -> m d -> m e -> m f)")
  1020. ("mapAndUnzipM" . "Monad m => (a -> m (b,c)) -> [a] -> m ([b], [c])")
  1021. ("mplus" . "MonadPlus m => m a -> m a -> m a")
  1022. ("msum" . "MonadPlus m => [m a] -> m a")
  1023. ("mzero" . "MonadPlus m => m a")
  1024. ("unless" . "Monad m => Bool -> m () -> m ()")
  1025. ("when" . "Monad m => Bool -> m () -> m ()")
  1026. ("zipWithM" . "Monad m => (a -> b -> m c) -> [a] -> [b] -> m [c]")
  1027. ("zipWithM_" . "Monad m => (a -> b -> m c) -> [a] -> [b] -> m ()")
  1028. ;; IO
  1029. ("bracket" . "IO a -> (a -> IO b) -> (a -> IO c) -> IO c")
  1030. ("bracket_" . "IO a -> (a -> IO b) -> IO c -> IO c")
  1031. ("hClose" . "Handle -> IO ()")
  1032. ("hFileSize" . "Handle -> IO Integer")
  1033. ("hFlush" . "Handle -> IO ()")
  1034. ("hGetBuffering" . "Handle -> IO BufferMode")
  1035. ("hGetChar" . "Handle -> IO Char")
  1036. ("hGetContents" . "Handle -> IO String")
  1037. ("hGetLine" . "Handle -> IO String")
  1038. ("hGetPosn" . "Handle -> IO HandlePosn")
  1039. ("hIsClosed" . "Handle -> IO Bool")
  1040. ("hIsEOF" . "Handle -> IO Bool")
  1041. ("hIsOpen" . "Handle -> IO Bool")
  1042. ("hIsReadable" . "Handle -> IO Bool")
  1043. ("hIsSeekable" . "Handle -> IO Bool")
  1044. ("hIsWritable" . "Handle -> IO Bool")
  1045. ("hLookAhead" . "Handle -> IO Char")
  1046. ("hPrint" . "Show a => Handle -> a -> IO ()")
  1047. ("hPutChar" . "Handle -> Char -> IO ()")
  1048. ("hPutStr" . "Handle -> String -> IO ()")
  1049. ("hPutStrLn" . "Handle -> String -> IO ()")
  1050. ("hReady" . "Handle -> IO Bool")
  1051. ("hSeek" . "Handle -> SeekMode -> Integer -> IO ()")
  1052. ("hSetBuffering" . "Handle -> BufferMode -> IO ()")
  1053. ("hSetPosn" . "HandlePosn -> IO ()")
  1054. ("hWaitForInput" . "Handle -> Int -> IO Bool")
  1055. ("ioeGetErrorString" . "IOError -> String")
  1056. ("ioeGetFileName" . "IOError -> Maybe FilePath")
  1057. ("ioeGetHandle" . "IOError -> Maybe Handle")
  1058. ("isAlreadyExistsError" . "IOError -> Bool")
  1059. ("isAlreadyInUseError" . "IOError -> Bool")
  1060. ("isDoesNotExistError" . "IOError -> Bool")
  1061. ("isEOF" . "IO Bool")
  1062. ("isEOFError" . "IOError -> Bool")
  1063. ("isFullError" . "IOError -> Bool")
  1064. ("isIllegalOperation" . "IOError -> Bool")
  1065. ("isPermissionError" . "IOError -> Bool")
  1066. ("isUserError" . "IOError -> Bool")
  1067. ("openFile" . "FilePath -> IOMode -> IO Handle")
  1068. ("stderr" . "Handle")
  1069. ("stdin" . "Handle")
  1070. ("stdout" . "Handle")
  1071. ("try" . "IO a -> IO (Either IOError a)")
  1072. ;; Directory
  1073. ("createDirectory" . "FilePath -> IO ()")
  1074. ("doesDirectoryExist" . "FilePath -> IO Bool")
  1075. ("doesFileExist" . "FilePath -> IO Bool")
  1076. ("executable" . "Permissions -> Bool")
  1077. ("getCurrentDirectory" . "IO FilePath")
  1078. ("getDirectoryContents" . "FilePath -> IO [FilePath]")
  1079. ("getModificationTime" . "FilePath -> IO ClockTime")
  1080. ("getPermissions" . "FilePath -> IO Permissions")
  1081. ("readable" . "Permissions -> Bool")
  1082. ("removeDirectory" . "FilePath -> IO ()")
  1083. ("removeFile" . "FilePath -> IO ()")
  1084. ("renameDirectory" . "FilePath -> FilePath -> IO ()")
  1085. ("renameFile" . "FilePath -> FilePath -> IO ()")
  1086. ("searchable" . "Permissions -> Bool")
  1087. ("setCurrentDirectory" . "FilePath -> IO ()")
  1088. ("setPermissions" . "FilePath -> Permissions -> IO ()")
  1089. ("writable" . "Permissions -> Bool")
  1090. ;; System
  1091. ("exitFailure" . "IO a")
  1092. ("exitWith" . "ExitCode -> IO a")
  1093. ("getArgs" . "IO [String]")
  1094. ("getEnv" . "String -> IO String")
  1095. ("getProgName" . "IO String")
  1096. ("system" . "String -> IO ExitCode")
  1097. ;; Time
  1098. ("addToClockTime" . "TimeDiff -> ClockTime -> ClockTime")
  1099. ("calendarTimeToString" . "CalendarTime -> String")
  1100. ("ctDay" . "CalendarTime -> Int")
  1101. ("ctHour" . "CalendarTime -> Int")
  1102. ("ctIsDST" . "CalendarTime -> Bool")
  1103. ("ctMin" . "CalendarTime -> Int")
  1104. ("ctMonth" . "CalendarTime -> Month")
  1105. ("ctPicosec" . "CalendarTime -> Integer")
  1106. ("ctSec" . "CalendarTime -> Int")
  1107. ("ctTZ" . "CalendarTime -> Int")
  1108. ("ctTZName" . "CalendarTime -> String")
  1109. ("ctWDay" . "CalendarTime -> Day")
  1110. ("ctYDay" . "CalendarTime -> Int")
  1111. ("ctYear" . "CalendarTime -> Int")
  1112. ("diffClockTimes" . "ClockTime -> ClockTime -> TimeDiff")
  1113. ("formatCalendarTime" . "TimeLocale -> String -> CalendarTime -> String")
  1114. ("getClockTime" . "IO ClockTime")
  1115. ("tdDay" . "TimeDiff -> Int")
  1116. ("tdHour" . "TimeDiff -> Int")
  1117. ("tdMin" . "TimeDiff -> Int")
  1118. ("tdMonth" . "TimeDiff -> Int")
  1119. ("tdPicosec" . "TimeDiff -> Integer")
  1120. ("tdSec" . "TimeDiff -> Int")
  1121. ("tdYear" . "TimeDiff -> Int")
  1122. ("toCalendarTime" . "ClockTime -> IO CalendarTime")
  1123. ("toClockTime" . "CalendarTime -> ClockTime")
  1124. ("toUTCTime" . "ClockTime -> CalendarTime")
  1125. ;; Locale
  1126. ("amPm" . "TimeLocale -> (String, String)")
  1127. ("dateFmt" . "TimeLocale -> String")
  1128. ("dateTimeFmt" . "TimeLocale -> String")
  1129. ("defaultTimeLocale" . "TimeLocale")
  1130. ("months" . "TimeLocale -> [(String, String)]")
  1131. ("time12Fmt" . "TimeLocale -> String")
  1132. ("timeFmt" . "TimeLocale -> String")
  1133. ("wDays" . "TimeLocale -> [(String, String)]")
  1134. ;; CPUTime
  1135. ("cpuTimePrecision" . "Integer")
  1136. ("getCPUTime" . "IO Integer")
  1137. ;; Random
  1138. ("genRange" . "RandomGen g => g -> (Int, Int)")
  1139. ("getStdGen" . "IO StdGen")
  1140. ("getStdRandom" . "(StdGen -> (a, StdGen)) -> IO a")
  1141. ("mkStdGen" . "Int -> StdGen")
  1142. ("newStdGen" . "IO StdGen")
  1143. ("next" . "RandomGen g => g -> (Int, g)")
  1144. ("random" . "(Random a, RandomGen g) => g -> (a, g)")
  1145. ("randomIO" . "Random a => IO a")
  1146. ("randomR" . "(Random a, RandomGen g) => (a, a) -> g -> (a, g)")
  1147. ("randomRIO" . "Random a => (a,a) -> IO a")
  1148. ("randomRs" . "(Random a, RandomGen g) => (a, a) -> g -> [a]")
  1149. ("randoms" . "(Random a, RandomGen g) => g -> [a]")
  1150. ("setStdGen" . "StdGen -> IO ()")
  1151. ("split" . "RandomGen g => g -> (g, g)")
  1152. )
  1153. "Alist of prelude functions and their types.")
  1154. ;;@cindex haskell-doc-strategy-ids
  1155. (defvar haskell-doc-strategy-ids
  1156. (list
  1157. '("par" . "Done -> Done -> Done ; [infixr 0]")
  1158. '("seq" . "Done -> Done -> Done ; [infixr 1]")
  1159. '("using" . "a -> Strategy a -> a ; [infixl 0]")
  1160. '("demanding" . "a -> Done -> a ; [infixl 0]")
  1161. '("sparking" . "a -> Done -> a ; [infixl 0]")
  1162. '(">||" . "Done -> Done -> Done ; [infixr 2]")
  1163. '(">|" . "Done -> Done -> Done ; [infixr 3]")
  1164. '("$||" . "(a -> b) -> Strategy a -> a -> b ; [infixl 6]")
  1165. '("$|" . "(a -> b) -> Strategy a -> a -> b ; [infixl 6]")
  1166. '(".|" . "(b -> c) -> Strategy b -> (a -> b) -> (a -> c) ; [infixl 9]")
  1167. '(".||" . "(b -> c) -> Strategy b -> (a -> b) -> (a -> c) ; [infixl 9]")
  1168. '("-|" . "(a -> b) -> Strategy b -> (b -> c) -> (a -> c) ; [infixl 9]")
  1169. '("-||" . "(a -> b) -> Strategy b -> (b -> c) -> (a -> c) ; [infixl 9]")
  1170. '("Done" . "type Done = ()")
  1171. '("Strategy" . "type Strategy a = a -> Done")
  1172. '("r0" . "Strategy a")
  1173. '("rwhnf" . "Eval a => Strategy a")
  1174. '("rnf" . "Strategy a")
  1175. '("NFData" . "class Eval a => NFData a where rnf :: Strategy a")
  1176. '("NFDataIntegral" ."class (NFData a, Integral a) => NFDataIntegral a")
  1177. '("NFDataOrd" . "class (NFData a, Ord a) => NFDataOrd a")
  1178. '("markStrat" . "Int -> Strategy a -> Strategy a")
  1179. '("seqPair" . "Strategy a -> Strategy b -> Strategy (a,b)")
  1180. '("parPair" . "Strategy a -> Strategy b -> Strategy (a,b)")
  1181. '("seqTriple" . "Strategy a -> Strategy b -> Strategy c -> Strategy (a,b,c)")
  1182. '("parTriple" . "Strategy a -> Strategy b -> Strategy c -> Strategy (a,b,c)")
  1183. '("parList" . "Strategy a -> Strategy [a]")
  1184. '("parListN" . "(Integral b) => b -> Strategy a -> Strategy [a]")
  1185. '("parListNth" . "Int -> Strategy a -> Strategy [a]")
  1186. '("parListChunk" . "Int -> Strategy a -> Strategy [a]")
  1187. '("parMap" . "Strategy b -> (a -> b) -> [a] -> [b]")
  1188. '("parFlatMap" . "Strategy [b] -> (a -> [b]) -> [a] -> [b]")
  1189. '("parZipWith" . "Strategy c -> (a -> b -> c) -> [a] -> [b] -> [c]")
  1190. '("seqList" . "Strategy a -> Strategy [a]")
  1191. '("seqListN" . "(Integral a) => a -> Strategy b -> Strategy [b]")
  1192. '("seqListNth" . "Int -> Strategy b -> Strategy [b]")
  1193. '("parBuffer" . "Int -> Strategy a -> [a] -> [a]")
  1194. '("seqArr" . "(Ix b) => Strategy a -> Strategy (Array b a)")
  1195. '("parArr" . "(Ix b) => Strategy a -> Strategy (Array b a)")
  1196. '("fstPairFstList" . "(NFData a) => Strategy [(a,b)]")
  1197. '("force" . "(NFData a) => a -> a ")
  1198. '("sforce" . "(NFData a) => a -> b -> b")
  1199. )
  1200. "Alist of strategy functions and their types as defined in Strategies.lhs.")
  1201. (defvar haskell-doc-user-defined-ids nil
  1202. "Alist of functions and strings defined by the user.")
  1203. ;;@node Test membership, , Prelude types, Constants and Variables
  1204. ;;@subsection Test membership
  1205. ;;@cindex haskell-doc-is-of
  1206. (defsubst haskell-doc-is-of (fn types)
  1207. "Check whether FN is one of the functions in the alist TYPES and return the type."
  1208. (assoc fn types) )
  1209. ;;@node Install as minor mode, Menubar Support, Constants and Variables, top
  1210. ;;@section Install as minor mode
  1211. ;; Put this minor mode on the global minor-mode-alist.
  1212. (or (assq 'haskell-doc-mode (default-value 'minor-mode-alist))
  1213. (setq-default minor-mode-alist
  1214. (append (default-value 'minor-mode-alist)
  1215. '((haskell-doc-mode haskell-doc-minor-mode-string)))))
  1216. ;;@node Menubar Support, Haskell Doc Mode, Install as minor mode, top
  1217. ;;@section Menubar Support
  1218. ;; get imenu
  1219. (require 'imenu)
  1220. ;; a dummy definition needed for XEmacs (I know, it's horrible :-(
  1221. ;;@cindex haskell-doc-install-keymap
  1222. (defvar haskell-doc-keymap
  1223. (let ((map (make-sparse-keymap)))
  1224. (define-key map [visit]
  1225. '("Visit FTP home site" . haskell-doc-visit-home))
  1226. (define-key map [submit]
  1227. '("Submit bug report" . haskell-doc-submit-bug-report))
  1228. (define-key map [dummy] '("---" . nil))
  1229. (define-key map [make-index]
  1230. '("Make global fct index" . haskell-doc-make-global-fct-index))
  1231. (define-key map [global-types-on]
  1232. '("Toggle display of global types" . haskell-doc-show-global-types))
  1233. (define-key map [strategy-on]
  1234. '("Toggle display of strategy ids" . haskell-doc-show-strategy))
  1235. (define-key map [user-defined-on]
  1236. '("Toggle display of user defined ids" . haskell-doc-show-user-defined))
  1237. (define-key map [prelude-on]
  1238. '("Toggle display of prelude functions" . haskell-doc-show-prelude))
  1239. (define-key map [reserved-ids-on]
  1240. '("Toggle display of reserved ids" . haskell-doc-show-reserved))
  1241. (define-key map [haskell-doc-on]
  1242. '("Toggle haskell-doc mode" . haskell-doc-mode))
  1243. map))
  1244. (defun haskell-doc-install-keymap ()
  1245. "Install a menu for `haskell-doc-mode' as a submenu of \"Hugs\"."
  1246. (interactive)
  1247. ;; Add the menu to the hugs menu as last entry.
  1248. (let ((hugsmap (lookup-key (current-local-map) [menu-bar Hugs])))
  1249. (if (not (or (featurep 'xemacs) ; XEmacs has problems here
  1250. (not (keymapp hugsmap))
  1251. (lookup-key hugsmap [haskell-doc])))
  1252. (if (functionp 'define-key-after)
  1253. (define-key-after hugsmap [haskell-doc]
  1254. (cons "Haskell-doc" haskell-doc-keymap)
  1255. [Haskell-doc mode]))))
  1256. ;; Add shortcuts for these commands.
  1257. (local-set-key "\C-c\e/" 'haskell-doc-check-active)
  1258. ;; Conflicts with the binding of haskell-insert-otherwise.
  1259. ;; (local-set-key "\C-c\C-o" 'haskell-doc-mode)
  1260. (local-set-key [(control shift meta mouse-3)]
  1261. 'haskell-doc-ask-mouse-for-type))
  1262. ;;@node Haskell Doc Mode, Switch it on or off, Menubar Support, top
  1263. ;;@section Haskell Doc Mode
  1264. ;;@cindex haskell-doc-mode
  1265. (defvar haskell-doc-timer nil)
  1266. (defvar haskell-doc-buffers nil)
  1267. ;;;###autoload
  1268. (defun haskell-doc-mode (&optional arg)
  1269. "Enter `haskell-doc-mode' for showing fct types in the echo area.
  1270. See variable docstring."
  1271. (interactive (list (or current-prefix-arg 'toggle)))
  1272. (setq haskell-doc-mode
  1273. (cond
  1274. ((eq arg 'toggle) (not haskell-doc-mode))
  1275. (arg (> (prefix-numeric-value arg) 0))
  1276. (t)))
  1277. ;; First, unconditionally turn the mode OFF.
  1278. (setq haskell-doc-buffers (delq (current-buffer) haskell-doc-buffers))
  1279. ;; Refresh the buffers list.
  1280. (dolist (buf haskell-doc-buffers)
  1281. (unless (and (buffer-live-p buf)
  1282. (with-current-buffer buf haskell-doc-mode))
  1283. (setq haskell-doc-buffers (delq buf haskell-doc-buffers))))
  1284. ;; Turn off the idle timer (or idle post-command-hook).
  1285. (when (and haskell-doc-timer (null haskell-doc-buffers))
  1286. (cancel-timer haskell-doc-timer)
  1287. (setq haskell-doc-timer nil))
  1288. (remove-hook 'post-command-hook
  1289. 'haskell-doc-mode-print-current-symbol-info 'local)
  1290. (when haskell-doc-mode
  1291. ;; Turning the mode ON.
  1292. (push (current-buffer) haskell-doc-buffers)
  1293. (if (fboundp 'run-with-idle-timer)
  1294. (unless haskell-doc-timer
  1295. (setq haskell-doc-timer
  1296. (run-with-idle-timer
  1297. haskell-doc-idle-delay t
  1298. 'haskell-doc-mode-print-current-symbol-info)))
  1299. (add-hook 'post-command-hook
  1300. 'haskell-doc-mode-print-current-symbol-info nil 'local))
  1301. (and haskell-doc-show-global-types
  1302. (haskell-doc-make-global-fct-index)) ; build type index for global fcts
  1303. (haskell-doc-install-keymap)
  1304. (run-hooks 'haskell-doc-mode-hook))
  1305. (and (interactive-p)
  1306. (message "haskell-doc-mode is %s"
  1307. (if haskell-doc-mode "enabled" "disabled")))
  1308. haskell-doc-mode)
  1309. (defmacro haskell-doc-toggle-var (id prefix)
  1310. ;; toggle variable or set it based on prefix value
  1311. `(setq ,id
  1312. (if ,prefix
  1313. (>= (prefix-numeric-value ,prefix) 0)
  1314. (not ,id))) )
  1315. ;;@cindex haskell-doc-show-global-types
  1316. (defun haskell-doc-show-global-types (&optional prefix)
  1317. "Turn on global types information in `haskell-doc-mode'."
  1318. (interactive "P")
  1319. (haskell-doc-toggle-var haskell-doc-show-global-types prefix)
  1320. (if haskell-doc-show-global-types
  1321. (haskell-doc-make-global-fct-index)))
  1322. ;;@cindex haskell-doc-show-reserved
  1323. (defun haskell-doc-show-reserved (&optional prefix)
  1324. "Toggle the automatic display of a doc string for reserved ids."
  1325. (interactive "P")
  1326. (haskell-doc-toggle-var haskell-doc-show-reserved prefix))
  1327. ;;@cindex haskell-doc-show-prelude
  1328. (defun haskell-doc-show-prelude (&optional prefix)
  1329. "Toggle the automatic display of a doc string for reserved ids."
  1330. (interactive "P")
  1331. (haskell-doc-toggle-var haskell-doc-show-prelude prefix))
  1332. ;;@cindex haskell-doc-show-strategy
  1333. (defun haskell-doc-show-strategy (&optional prefix)
  1334. "Toggle the automatic display of a doc string for strategy ids."
  1335. (interactive "P")
  1336. (haskell-doc-toggle-var haskell-doc-show-strategy prefix))
  1337. ;;@cindex haskell-doc-show-user-defined
  1338. (defun haskell-doc-show-user-defined (&optional prefix)
  1339. "Toggle the automatic display of a doc string for user defined ids."
  1340. (interactive "P")
  1341. (haskell-doc-toggle-var haskell-doc-show-user-defined prefix))
  1342. ;;@node Switch it on or off, Check, Haskell Doc Mode, top
  1343. ;;@section Switch it on or off
  1344. ;;@cindex turn-on-haskell-doc-mode
  1345. ;;;###autoload
  1346. (defalias 'turn-on-haskell-doc-mode 'haskell-doc-mode)
  1347. ;;@cindex turn-off-haskell-doc-mode
  1348. (defun turn-off-haskell-doc-mode ()
  1349. "Unequivocally turn off `haskell-doc-mode' (which see)."
  1350. (haskell-doc-mode 0))
  1351. ;;@node Check, Top level function, Switch it on or off, top
  1352. ;;@section Check
  1353. ;;@cindex haskell-doc-check-active
  1354. (defun haskell-doc-check-active ()
  1355. "Check whether the print function is hooked in.
  1356. Should be the same as the value of `haskell-doc-mode' but alas currently it
  1357. is not."
  1358. (interactive)
  1359. (message "%s"
  1360. (if (or (and haskell-doc-mode haskell-doc-timer)
  1361. (memq 'haskell-doc-mode-print-current-symbol-info
  1362. post-command-hook))
  1363. "haskell-doc is ACTIVE"
  1364. (substitute-command-keys
  1365. "haskell-doc is not ACTIVE \(Use \\[haskell-doc-mode] to turn it on\)"))))
  1366. ;;@node Top level function, Mouse interface, Check, top
  1367. ;;@section Top level function
  1368. ;;@cindex haskell-doc-mode-print-current-symbol-info
  1369. ;; This is the function hooked into the elisp command engine
  1370. (defun haskell-doc-mode-print-current-symbol-info ()
  1371. "Print the type of the symbol under the cursor.
  1372. This function is run by an idle timer to print the type
  1373. automatically if `haskell-doc-mode' is turned on."
  1374. (and haskell-doc-mode
  1375. (not executing-kbd-macro)
  1376. ;; Having this mode operate in the minibuffer makes it impossible to
  1377. ;; see what you're doing.
  1378. (not (eq (selected-window) (minibuffer-window)))
  1379. ;; take a nap, if run straight from post-command-hook.
  1380. (if (fboundp 'run-with-idle-timer) t
  1381. (sit-for haskell-doc-idle-delay))
  1382. ;; good morning! read the word under the cursor for breakfast
  1383. (haskell-doc-show-type)))
  1384. ;; ;; ToDo: find surrounding fct
  1385. ;; (cond ((eq current-symbol current-fnsym)
  1386. ;; (haskell-doc-show-type current-fnsym))
  1387. ;; (t
  1388. ;; (or nil ; (haskell-doc-print-var-docstring current-symbol)
  1389. ;; (haskell-doc-show-type current-fnsym)))))))
  1390. (defun haskell-doc-current-info ()
  1391. "Return the info about symbol at point.
  1392. Meant for `eldoc-documentation-function'."
  1393. (haskell-doc-sym-doc (haskell-ident-at-point)))
  1394. ;;@node Mouse interface, Print fctsym, Top level function, top
  1395. ;;@section Mouse interface for interactive query
  1396. ;;@cindex haskell-doc-ask-mouse-for-type
  1397. (defun haskell-doc-ask-mouse-for-type (event)
  1398. "Read the identifier under the mouse and echo its type.
  1399. This uses the same underlying function `haskell-doc-show-type' as the hooked
  1400. function. Only the user interface is different."
  1401. (interactive "e")
  1402. (save-excursion
  1403. (select-window (posn-window (event-end event)))
  1404. (goto-char (posn-point (event-end event)))
  1405. (haskell-doc-show-type)))
  1406. ;;@node Print fctsym, Movement, Mouse interface, top
  1407. ;;@section Print fctsym
  1408. ;;@menu
  1409. ;;* Show type::
  1410. ;;* Aux::
  1411. ;;* Global fct type::
  1412. ;;* Local fct type::
  1413. ;;@end menu
  1414. ;;@node Show type, Aux, Print fctsym, Print fctsym
  1415. ;;@subsection Show type
  1416. ;;@cindex haskell-doc-show-type
  1417. (require 'syntax-ppss nil t) ; possible add-on in Emacs 21
  1418. (defun haskell-doc-in-code-p ()
  1419. (not (or (and (eq haskell-literate 'bird)
  1420. ;; Copied from haskell-indent-bolp.
  1421. (<= (current-column) 2)
  1422. (eq (char-after (line-beginning-position)) ?\>))
  1423. (if (fboundp 'syntax-ppss)
  1424. (nth 8 (syntax-ppss))))))
  1425. ;;;###autoload
  1426. (defun haskell-doc-show-type (&optional sym)
  1427. "Show the type of the function near point.
  1428. For the function under point, show the type in the echo area.
  1429. This information is extracted from the `haskell-doc-prelude-types' alist
  1430. of prelude functions and their types, or from the local functions in the
  1431. current buffer."
  1432. (interactive)
  1433. (unless sym (setq sym (haskell-ident-at-point)))
  1434. ;; if printed before do not print it again
  1435. (unless (string= sym (car haskell-doc-last-data))
  1436. (let ((doc (haskell-doc-sym-doc sym)))
  1437. (when (and doc (haskell-doc-in-code-p))
  1438. ;; In Emacs 19.29 and later, and XEmacs 19.13 and later, all
  1439. ;; messages are recorded in a log. Do not put haskell-doc messages
  1440. ;; in that log since they are legion.
  1441. (if (eval-when-compile (fboundp 'display-message))
  1442. ;; XEmacs 19.13 way of preventing log messages.
  1443. ;;(display-message 'no-log (format <args>))
  1444. ;; XEmacs 19.15 seems to be a bit different.
  1445. (display-message 'message (format "%s" doc))
  1446. (let ((message-log-max nil))
  1447. (message "%s" doc)))))))
  1448. (defun haskell-doc-sym-doc (sym)
  1449. "Show the type of the function near point.
  1450. For the function under point, show the type in the echo area.
  1451. This information is extracted from the `haskell-doc-prelude-types' alist
  1452. of prelude functions and their types, or from the local functions in the
  1453. current buffer."
  1454. (let ((i-am-prelude nil)
  1455. (i-am-fct nil)
  1456. (type nil)
  1457. (is-reserved (haskell-doc-is-of sym haskell-doc-reserved-ids))
  1458. (is-prelude (haskell-doc-is-of sym haskell-doc-prelude-types))
  1459. (is-strategy (haskell-doc-is-of sym haskell-doc-strategy-ids))
  1460. (is-user-defined (haskell-doc-is-of sym haskell-doc-user-defined-ids))
  1461. (is-prelude (haskell-doc-is-of sym haskell-doc-prelude-types)))
  1462. (cond
  1463. ;; if reserved id (i.e. Haskell keyword
  1464. ((and haskell-doc-show-reserved
  1465. is-reserved)
  1466. (setq type (cdr is-reserved))
  1467. (setcdr haskell-doc-last-data type))
  1468. ;; if built-in function get type from docstring
  1469. ((and (not (null haskell-doc-show-prelude))
  1470. is-prelude)
  1471. (setq type (cdr is-prelude)) ; (cdr (assoc sym haskell-doc-prelude-types)))
  1472. (if (= 2 (length type)) ; horrible hack to remove bad formatting
  1473. (setq type (car (cdr type))))
  1474. (setq i-am-prelude t)
  1475. (setq i-am-fct t)
  1476. (setcdr haskell-doc-last-data type))
  1477. ((and haskell-doc-show-strategy
  1478. is-strategy)
  1479. (setq i-am-fct t)
  1480. (setq type (cdr is-strategy))
  1481. (setcdr haskell-doc-last-data type))
  1482. ((and haskell-doc-show-user-defined
  1483. is-user-defined)
  1484. ;; (setq i-am-fct t)
  1485. (setq type (cdr is-user-defined))
  1486. (setcdr haskell-doc-last-data type))
  1487. (t
  1488. (let ( (x (haskell-doc-get-and-format-fct-type sym)) )
  1489. (if (null x)
  1490. (setcdr haskell-doc-last-data nil) ; if not found reset last data
  1491. (setq type (car x))
  1492. (setq i-am-fct (string= "Variables" (cdr x)))
  1493. (if (and haskell-doc-show-global-types (null type))
  1494. (setq type (haskell-doc-get-global-fct-type sym)))
  1495. (setcdr haskell-doc-last-data type)))) )
  1496. ;; ToDo: encode i-am-fct info into alist of types
  1497. (and type
  1498. ;; drop `::' if it's not a fct
  1499. (let ( (str (cond ((and i-am-fct (not haskell-doc-chop-off-fctname))
  1500. (format "%s :: %s" sym type))
  1501. (t
  1502. (format "%s" type)))) )
  1503. (if i-am-prelude
  1504. (add-text-properties 0 (length str) '(face bold) str))
  1505. str))))
  1506. ;; ToDo: define your own notion of `near' to find surrounding fct
  1507. ;;(defun haskell-doc-fnsym-in-current-sexp ()
  1508. ;; (let* ((p (point))
  1509. ;; (sym (progn
  1510. ;; (forward-word -1)
  1511. ;; (while (and (forward-word -1) ; (haskell-doc-forward-sexp-safe -1)
  1512. ;; (> (point) (point-min))))
  1513. ;; (cond ((or (= (point) (point-min))
  1514. ;; (memq (or (char-after (point)) 0)
  1515. ;; '(?\( ?\"))
  1516. ;; ;; If we hit a quotation mark before a paren, we
  1517. ;; ;; are inside a specific string, not a list of
  1518. ;; ;; symbols.
  1519. ;; (eq (or (char-after (1- (point))) 0) ?\"))
  1520. ;; nil)
  1521. ;; (t (condition-case nil
  1522. ;; (read (current-buffer))
  1523. ;; (error nil)))))))
  1524. ;; (goto-char p)
  1525. ;; (if sym
  1526. ;; (format "%s" sym)
  1527. ;; sym)))
  1528. ;; (and (symbolp sym)
  1529. ;; sym)))
  1530. ;;@node Aux, Global fct type, Show type, Print fctsym
  1531. ;;@subsection Aux
  1532. ;; ToDo: handle open brackets to decide if it's a wrapped type
  1533. ;;@cindex haskell-doc-grab-line
  1534. (defun haskell-doc-grab-line (fct-and-pos)
  1535. "Get the type of an \(FCT POSITION\) pair from the current buffer."
  1536. ;; (if (null fct-and-pos)
  1537. ;; "" ; fn is not a local fct
  1538. (let ( (str ""))
  1539. (goto-char (cdr fct-and-pos))
  1540. (beginning-of-line)
  1541. ;; search for start of type (phsp give better bound?)
  1542. (if (null (search-forward "::" (+ (point) haskell-doc-search-distance) t))
  1543. ""
  1544. (setq str (haskell-doc-grab)) ; leaves point at end of line
  1545. (while (haskell-doc-wrapped-type-p) ; while in a multi-line type expr
  1546. (forward-line 1)
  1547. (beginning-of-line)
  1548. (skip-chars-forward " \t")
  1549. (setq str (concat str (haskell-doc-grab))))
  1550. (haskell-doc-string-nub-ws ; squeeze string
  1551. (if haskell-doc-chop-off-context ; no context
  1552. (haskell-doc-chop-off-context str)
  1553. str)))))
  1554. ;; (concat (car fct-and-pos) "::" (haskell-doc-string-nub-ws str))))
  1555. ;;@cindex haskell-doc-wrapped-type-p
  1556. (defun haskell-doc-wrapped-type-p ()
  1557. "Check whether the type under the cursor is wrapped over several lines.
  1558. The cursor must be at the end of a line, which contains the type.
  1559. Currently, only the following is checked:
  1560. If this line ends with a `->' or the next starts with an `->' it is a
  1561. multi-line type \(same for `=>'\).
  1562. `--' comments are ignored.
  1563. ToDo: Check for matching parenthesis!."
  1564. (save-excursion
  1565. (let ( (here (point))
  1566. (lim (progn (beginning-of-line) (point)))
  1567. ;; (foo "")
  1568. (res nil)
  1569. )
  1570. (goto-char here)
  1571. (search-backward "--" lim t) ; skip over `--' comment
  1572. (skip-chars-backward " \t")
  1573. (if (bolp) ; skip empty lines
  1574. (progn
  1575. (forward-line 1)
  1576. (end-of-line)
  1577. (setq res (haskell-doc-wrapped-type-p)))
  1578. (forward-char -1)
  1579. ;; (setq foo (concat foo (char-to-string (preceding-char)) (char-to-string (following-char))))
  1580. (if (or (and (or (char-equal (preceding-char) ?-) (char-equal (preceding-char) ?=))
  1581. (char-equal (following-char) ?>)) ; (or -!> =!>
  1582. (char-equal (following-char) ?,)) ; !,)
  1583. (setq res t)
  1584. (forward-line)
  1585. (let ((here (point)))
  1586. (goto-char here)
  1587. (skip-chars-forward " \t")
  1588. (if (looking-at "--") ; it is a comment line
  1589. (progn
  1590. (forward-line 1)
  1591. (end-of-line)
  1592. (setq res (haskell-doc-wrapped-type-p)))
  1593. (forward-char 1)
  1594. ;; (setq foo (concat foo (char-to-string (preceding-char)) (char-to-string (following-char))))
  1595. ;; (message "|%s|" foo)
  1596. (if (and (or (char-equal (preceding-char) ?-) (char-equal (preceding-char) ?=))
  1597. (char-equal (following-char) ?>)) ; -!> or =!>
  1598. (setq res t))))))
  1599. res)))
  1600. ;;@cindex haskell-doc-grab
  1601. (defun haskell-doc-grab ()
  1602. "Return the text from point to the end of the line, chopping off comments.
  1603. Leaves point at end of line."
  1604. (let ((str (buffer-substring-no-properties
  1605. (point) (progn (end-of-line) (point)))))
  1606. (if (string-match "--" str)
  1607. (substring str 0 (match-beginning 0))
  1608. str)))
  1609. ;;@cindex haskell-doc-string-nub-ws
  1610. (defun haskell-doc-string-nub-ws (str)
  1611. "Replace all sequences of whitespace in STR by just one space.
  1612. ToDo: Also eliminate leading and trailing whitespace."
  1613. (let ((i -1))
  1614. (while (setq i (string-match " [ \t\n]+\\|[\t\n]+" str (1+ i)))
  1615. (setq str (replace-match " " t t str)))
  1616. str))
  1617. ;; ToDo: make this more efficient!!
  1618. ;;(defun haskell-doc-string-nub-ws (str)
  1619. ;; "Replace all sequences of whitespaces in STR by just one whitespace."
  1620. ;; (let ( (res "")
  1621. ;; (l (length str))
  1622. ;; (i 0)
  1623. ;; (j 0)
  1624. ;; (in-ws nil))
  1625. ;; (while (< i l)
  1626. ;; (let* ( (c (string-to-char (substring str i (1+ i))))
  1627. ;; (is-ws (eq (char-syntax c) ? )) )
  1628. ;; (if (not (and in-ws is-ws))
  1629. ;; (setq res (concat res (char-to-string c))))
  1630. ;; (setq in-ws is-ws)
  1631. ;; (setq i (1+ i))))
  1632. ;; res))
  1633. ;;@cindex haskell-doc-chop-off-context
  1634. (defun haskell-doc-chop-off-context (str)
  1635. "Eliminate the context in a type represented by the string STR."
  1636. (let ((i (string-match "=>" str)) )
  1637. (if (null i)
  1638. str
  1639. (substring str (+ i 2)))))
  1640. ;;@cindex haskell-doc-get-imenu-info
  1641. (defun haskell-doc-get-imenu-info (obj kind)
  1642. "Return a string describing OBJ of KIND \(Variables, Types, Data\)."
  1643. (cond ((or (eq major-mode 'haskell-hugs-mode)
  1644. ;; GEM: Haskell Mode does not work with Haskell Doc
  1645. ;; under XEmacs 20.x
  1646. (and (eq major-mode 'haskell-mode)
  1647. (not (and (featurep 'xemacs)
  1648. (string-match "^20" emacs-version)))))
  1649. (let* ((imenu-info-alist (cdr (assoc kind imenu--index-alist)))
  1650. ;; (names (mapcar 'car imenu-info-alist))
  1651. (x (assoc obj imenu-info-alist)))
  1652. (if x
  1653. (haskell-doc-grab-line x)
  1654. nil)))
  1655. (t
  1656. ;; (error "Cannot get local functions in %s mode, sorry" major-mode))) )
  1657. nil)))
  1658. ;;@node Global fct type, Local fct type, Aux, Print fctsym
  1659. ;;@subsection Global fct type
  1660. ;; ToDo:
  1661. ;; - modular way of defining a mapping of module name to file
  1662. ;; - use a path to search for file (not just current directory)
  1663. ;;@cindex haskell-doc-imported-list
  1664. (defun haskell-doc-imported-list ()
  1665. "Return a list of the imported modules in current buffer."
  1666. (interactive "fName of outer `include' file: ") ; (buffer-file-name))
  1667. ;; Don't add current buffer to the imported file list if it is not (yet?)
  1668. ;; visiting a file since it leads to errors further down.
  1669. (let ((imported-file-list (and buffer-file-name (list buffer-file-name))))
  1670. (widen)
  1671. (goto-char (point-min))
  1672. (while (re-search-forward "^\\s-*import\\s-+\\([^ \t\n]+\\)" nil t)
  1673. (let ((basename (match-string 1)))
  1674. (dolist (ext '(".hs" ".lhs"))
  1675. (let ((file (concat basename ext)))
  1676. (if (file-exists-p file)
  1677. (push file imported-file-list))))))
  1678. (nreverse imported-file-list)
  1679. ;;(message imported-file-list)
  1680. ))
  1681. ;; ToDo: generalise this to "Types" etc (not just "Variables")
  1682. ;;@cindex haskell-doc-rescan-files
  1683. (defun haskell-doc-rescan-files (filelist)
  1684. "Do an `imenu' rescan on every file in FILELIST and return the fct-list.
  1685. This function switches to and potentially loads many buffers."
  1686. (save-current-buffer
  1687. (mapcar (lambda (f)
  1688. (set-buffer (find-file-noselect f))
  1689. (imenu--make-index-alist)
  1690. (cons f
  1691. (mapcar (lambda (x)
  1692. `(,(car x) . ,(haskell-doc-grab-line x)))
  1693. (cdr (assoc "Variables" imenu--index-alist)))))
  1694. filelist)))
  1695. ;;@cindex haskell-doc-make-global-fct-index
  1696. (defun haskell-doc-make-global-fct-index ()
  1697. "Scan imported files for types of global fcts and update `haskell-doc-index'."
  1698. (interactive)
  1699. (setq haskell-doc-index
  1700. (haskell-doc-rescan-files (haskell-doc-imported-list))))
  1701. ;; ToDo: use a separate munge-type function to format type concisely
  1702. ;;@cindex haskell-doc-get-global-fct-type
  1703. (defun haskell-doc-get-global-fct-type (&optional sym)
  1704. "Get type for function symbol SYM by examining `haskell-doc-index'."
  1705. (interactive) ; "fName of outer `include' file: \nsFct:")
  1706. (save-excursion
  1707. ;; (switch-to-buffer "*scratch*")
  1708. ;; (goto-char (point-max))
  1709. ;; ;; Produces a list of fct-type alists
  1710. ;; (if (null sym)
  1711. ;; (setq sym (progn (forward-word -1) (read (current-buffer)))))
  1712. (or sym
  1713. (current-word))
  1714. (let* ( (fn sym) ; (format "%s" sym))
  1715. (fal haskell-doc-index)
  1716. (res "") )
  1717. (while (not (null fal))
  1718. (let* ( (l (car fal))
  1719. (f (car l))
  1720. (x (assoc fn (cdr l))) )
  1721. (if (not (null x))
  1722. (let* ( (ty (cdr x)) ; the type as string
  1723. (idx (string-match "::" ty))
  1724. (str (if (null idx)
  1725. ty
  1726. (substring ty (+ idx 2)))) )
  1727. (setq res (format "[%s] %s" f str))))
  1728. (setq fal (cdr fal))))
  1729. res))) ; (message res)) )
  1730. ;;@node Local fct type, , Global fct type, Print fctsym
  1731. ;;@subsection Local fct type
  1732. ;;@cindex haskell-doc-get-and-format-fct-type
  1733. (defun haskell-doc-get-and-format-fct-type (fn)
  1734. "Get the type and kind of FN by checking local and global functions."
  1735. (save-excursion
  1736. (save-match-data
  1737. (let ((docstring "")
  1738. (doc nil)
  1739. )
  1740. ;; is it a local function?
  1741. (setq docstring (haskell-doc-get-imenu-info fn "Variables"))
  1742. (if (not (null docstring))
  1743. ;; (string-match (format "^%s\\s-+::\\s-+\\(.*\\)$" fn) docstring))
  1744. (setq doc `(,docstring . "Variables"))) ; `(,(match-string 1 docstring) . "Variables") ))
  1745. ;; is it a type declaration?
  1746. (setq docstring (haskell-doc-get-imenu-info fn "Types"))
  1747. (if (not (null docstring))
  1748. ;; (string-match (format "^\\s-*type\\s-+%s.*$" fn) docstring))
  1749. (setq doc `(,docstring . "Types"))) ; `(,(match-string 0 docstring) . "Types")) )
  1750. (if (not (null docstring))
  1751. ;; (string-match (format "^\\s-*data.*%s.*$" fn) docstring))
  1752. (setq doc `(,docstring . "Data"))) ; (setq doc `(,(match-string 0 docstring) . "Data")) )
  1753. ;; return the result
  1754. doc ))))
  1755. ;;@appendix
  1756. ;;@node Index, Token, Visit home site, top
  1757. ;;@section Index
  1758. ;;@index
  1759. ;;* haskell-doc-ask-mouse-for-type::
  1760. ;;* haskell-doc-check-active::
  1761. ;;* haskell-doc-chop-off-context::
  1762. ;;* haskell-doc-get-and-format-fct-type::
  1763. ;;* haskell-doc-get-global-fct-type::
  1764. ;;* haskell-doc-get-imenu-info::
  1765. ;;* haskell-doc-grab::
  1766. ;;* haskell-doc-grab-line::
  1767. ;;* haskell-doc-imported-list::
  1768. ;;* haskell-doc-install-keymap::
  1769. ;;* haskell-doc-is-of::
  1770. ;;* haskell-doc-make-global-fct-index::
  1771. ;;* haskell-doc-mode::
  1772. ;;* haskell-doc-mode-print-current-symbol-info::
  1773. ;;* haskell-doc-prelude-types::
  1774. ;;* haskell-doc-rescan-files::
  1775. ;;* haskell-doc-reserved-ids::
  1776. ;;* haskell-doc-show-global-types::
  1777. ;;* haskell-doc-show-prelude::
  1778. ;;* haskell-doc-show-reserved::
  1779. ;;* haskell-doc-show-strategy::
  1780. ;;* haskell-doc-show-type::
  1781. ;;* haskell-doc-show-user-defined::
  1782. ;;* haskell-doc-strategy-ids::
  1783. ;;* haskell-doc-string-nub-ws::
  1784. ;;* haskell-doc-submit-bug-report::
  1785. ;;* haskell-doc-visit-home::
  1786. ;;* haskell-doc-wrapped-type-p::
  1787. ;;* turn-off-haskell-doc-mode::
  1788. ;;* turn-on-haskell-doc-mode::
  1789. ;;@end index
  1790. ;;@node Token, , Index, top
  1791. ;;@section Token
  1792. (provide 'haskell-doc)
  1793. ;; arch-tag: 6492eb7e-7048-47ac-a331-da09e1eb6254
  1794. ;;; haskell-doc.el ends here