unofficial mirror of emacs-devel@gnu.org 
 help / color / mirror / code / Atom feed
* {ispell,flyspell}.el and coexistence of ispell and aspell
@ 2006-09-28 10:06 Agustin Martin
  2006-10-01 22:25 ` Richard Stallman
  0 siblings, 1 reply; 3+ messages in thread
From: Agustin Martin @ 2006-09-28 10:06 UTC (permalink / raw)


[-- Attachment #1: Type: text/plain, Size: 2849 bytes --]

Hi,

I have been playing with a rather unusual process, having ispell and aspell
dict for the same language and using the ispell one after having previously
selected aspell. This changes ispell-dictionary-alist to the aspell
one and can produce some problems in that unusual case, as well as in others
where ispell is used after aspell.

a) Run emacs with aspell as default

  After ispell.el is loaded, ispell-library-directory is nil, because that
  is what ispell-check-version returns for aspell.

  ispell-change-dictionary shows the full aspell list as expected.

b) Customize ispell-program-name to ispell.

  ispell-change-dictionary shows the full aspell list, including many dicts
  non available for ispell, because ispell-library-directory is nil.

  ispell-library-directory and so ispell-valid-dictionary-list are again set
  to the right value after an spellchecking command involving a call to
  ispell-init-process is issued, but this is not fully correct because values
  for the ispell dict options having an aspell dict with the same name are
  still the aspell ones, which have overriden the original ones, and the
  original values are lost. This can lead to errors in the ispell call
  (first need to kill aspell process, see below).

  Furthermore, if an aspell process was active, and the dictionary selected
  after ispell-program-name customization has the same name than the
  previous aspell one, aspell process is not killed and no new ispell process
  is started, aspell is still in use.

I am attaching a couple of patches for ispell.el and flyspell.el with the
setup I am trying here. It relies on a new (ispell-initialize-program-params)
function that is run when an spellchecking command is called for the first
time or after ispell-program-name change. Two alists of dicts are maintained
separately, original list is now ispell-base-dictionary-alist and aspell one
is ispell-aspell-dictionary-alist, filled when needed from
(ispell-initialize-program-params) through a call to
(ispell-find-aspell-dictionaries). ispell-dictionary-alist is an alist whose
value is set from (ispell-initialize-program-params) according to
ispell-really-aspell value. Also (ispell-initialize-ispell) takes care of
killing old ispell process when ispell-program-name is changed.

Calls to (ispell-maybe-find-aspell-dictionaries) are replaced by calls to this
(ispell-initialize-program-params) function, as well as a call to
(ispell-check-version) in (flyspell-large-region).

I think something like this is better for the future, if some other
spellchecker is to be supported (hunspell, that also supports an -a option,
comes to my mind), a function to get correct dict list and some code in
(ispell-initialize-program-params) should help.

Let me know if this is reasonable, so I provide a changelog entry.

Comments? 

-- 
Agustin

[-- Attachment #2: flyspell.el_ispell-initialize-program-params.diff --]
[-- Type: text/plain, Size: 836 bytes --]

--- flyspell.el.orig	2006-09-14 14:57:12.000000000 +0200
+++ flyspell.el	2006-09-14 14:57:26.000000000 +0200
@@ -556,7 +556,7 @@
 ;;*---------------------------------------------------------------------*/
 (defun flyspell-mode-on ()
   "Turn Flyspell mode on.  Do not use this; use `flyspell-mode' instead."
-  (ispell-maybe-find-aspell-dictionaries)
+  (ispell-initialize-program-params)
   (setq ispell-highlight-face 'flyspell-incorrect)
   ;; local dictionaries setup
   (or ispell-local-dictionary ispell-dictionary
@@ -1476,7 +1476,7 @@
     ;; this is done, we can start checking...
     (if flyspell-issue-message-flag (message "Checking region..."))
     (set-buffer curbuf)
-    (ispell-check-version)
+    (ispell-initialize-program-params)
     (let ((c (apply 'call-process-region beg
 		    end
 		    ispell-program-name

[-- Attachment #3: ispell.el_ispell-initialize-program-params.diff --]
[-- Type: text/plain, Size: 5689 bytes --]

--- ispell.el.orig	2006-09-14 14:59:04.000000000 +0200
+++ ispell.el	2006-09-14 15:08:48.000000000 +0200
@@ -659,11 +659,11 @@
 
 
 ;;;###autoload
-(defvar ispell-dictionary-alist
+(defvar ispell-base-dictionary-alist
   (append ispell-dictionary-alist-1 ispell-dictionary-alist-2
 	  ispell-dictionary-alist-3 ispell-dictionary-alist-4
 	  ispell-dictionary-alist-5 ispell-dictionary-alist-6)
-  "An alist of dictionaries and their associated parameters.
+  "Base alist of dictionaries and their associated parameters.
 
 Each element of this list is also a list:
 
@@ -716,6 +716,15 @@
 contain the same character set as casechars and otherchars in the
 LANGUAGE.aff file \(e.g., english.aff\).")
 
+;;;###autoload
+(defvar ispell-dictionary-alist ispell-base-dictionary-alist
+  "Runtime alist of dictionaries and their associated parameters,
+matching the right spellchecker")
+
+(defvar ispell-aspell-dictionary-alist nil
+  "An alist to be filled with the list of available aspell dicts
+and their associated parameters")
+
 (defvar ispell-really-aspell nil) ; Non-nil if aspell extensions should be used
 
 (defvar ispell-aspell-supports-utf8 nil
@@ -725,8 +734,6 @@
 Earlier aspell versions do not consistently support UTF-8.  Handling
 this would require some extra guessing in `ispell-aspell-find-dictionary'.")
 
-
-
 ;;; **********************************************************************
 ;;; The following are used by ispell, and should not be changed.
 ;;; **********************************************************************
@@ -876,18 +883,30 @@
 
 ;; Make ispell.el work better with aspell.
 
-(defvar ispell-have-aspell-dictionaries nil
-  "Non-nil if we have queried Aspell for dictionaries at least once.")
-
-(defun ispell-maybe-find-aspell-dictionaries ()
-  "Find Aspell's dictionaries, unless already done."
-  (when (and (not ispell-have-aspell-dictionaries)
-	     (condition-case ()
-		 (progn (ispell-check-version) t)
+(defvar ispell-last-program-name nil
+  "Will store the value of `ispell-program-name' used in
+last spellchecking command.")
+
+(defun ispell-initialize-program-params ( &optional force )
+  "Initialize ispell.el if not yet done or `ispell-program-name'
+is changed, setting the right dictionary alist.
+FORCE will re-initialize unconditionally"
+  (when (or (not (eq ispell-last-program-name ispell-program-name))
+	    force)
+    (ispell-kill-ispell t)
+    (if (and (condition-case ()
+		 (progn
+		   (setq ispell-library-directory (ispell-check-version))
+		   t)
 	       (error nil))
 	     ispell-really-aspell
 	     ispell-aspell-supports-utf8)
-    (ispell-find-aspell-dictionaries)))
+	(progn
+	  (if (not ispell-aspell-dictionary-alist)
+	      (ispell-find-aspell-dictionaries))
+	  (setq ispell-dictionary-alist ispell-aspell-dictionary-alist))
+      (setq ispell-dictionary-alist ispell-base-dictionary-alist))
+    (setq ispell-last-program-name ispell-program-name)))
 
 (defun ispell-find-aspell-dictionaries ()
   "Find Aspell's dictionaries, and record in `ispell-dictionary-alist'."
@@ -907,17 +926,16 @@
     (setq found (ispell-aspell-add-aliases found))
     ;; Merge into FOUND any elements from the standard ispell-dictionary-alist
     ;; which have no element in FOUND at all.    
-    (dolist (dict ispell-dictionary-alist)
+    (dolist (dict ispell-base-dictionary-alist)
       (unless (assoc (car dict) found)
 	(setq found (nconc found (list dict)))))
-    (setq ispell-dictionary-alist found)
+    (setq ispell-aspell-dictionary-alist found)
     ;; Add a default entry
-    (let* ((english-dict (assoc "en" ispell-dictionary-alist))
+    (let* ((english-dict (assoc "en" ispell-aspell-dictionary-alist))
 	   (default-dict
 	     (cons nil (or (cdr english-dict)
 			   (cdr (car ispell-dictionary-alist-1))))))
-      (push default-dict ispell-dictionary-alist))
-    (setq ispell-have-aspell-dictionaries t)))
+      (push default-dict ispell-aspell-dictionary-alist))))
 
 (defvar ispell-aspell-data-dir nil
   "Data directory of Aspell.")
@@ -1002,8 +1020,8 @@
 (defun ispell-valid-dictionary-list ()
   "Returns a list of valid dictionaries.
 The variable `ispell-library-directory' defines the library location."
-  ;; If Ispell is really Aspell, query it for the dictionary list.
-  (ispell-maybe-find-aspell-dictionaries)
+  ;; Make sure ispell program is initialized (right dicts lists, paths, ...)
+  (ispell-initialize-program-params)
   (let ((dicts (append ispell-local-dictionary-alist ispell-dictionary-alist))
 	(dict-list (cons "default" nil))
 	name load-dict)
@@ -1582,7 +1600,7 @@
   (interactive (list ispell-following-word ispell-quietly current-prefix-arg))
   (if continue
       (ispell-continue)
-    (ispell-maybe-find-aspell-dictionaries)
+    (ispell-initialize-program-params)
     (ispell-accept-buffer-local-defs)	; use the correct dictionary
     (let ((cursor-location (point))	; retain cursor location
 	  (word (ispell-get-word following))
@@ -2600,6 +2618,7 @@
 Without a prefix arg, set it \"locally\", just for this buffer.
 
 By just answering RET you can find out what the current dictionary is."
+  (ispell-initialize-program-params)
   (interactive
    (list (completing-read
 	  "Use new dictionary (RET for current, SPC to complete): "
@@ -2656,7 +2675,7 @@
 Return nil if spell session is quit,
  otherwise returns shift offset amount for last line processed."
   (interactive "r")			; Don't flag errors on read-only bufs.
-  (ispell-maybe-find-aspell-dictionaries)
+  (ispell-initialize-program-params)
   (if (not recheckp)
       (ispell-accept-buffer-local-defs)) ; set up dictionary, local words, etc.
   (let ((skip-region-start (make-marker))

[-- Attachment #4: Type: text/plain, Size: 142 bytes --]

_______________________________________________
Emacs-devel mailing list
Emacs-devel@gnu.org
http://lists.gnu.org/mailman/listinfo/emacs-devel

^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: {ispell,flyspell}.el and coexistence of ispell and aspell
  2006-09-28 10:06 {ispell,flyspell}.el and coexistence of ispell and aspell Agustin Martin
@ 2006-10-01 22:25 ` Richard Stallman
  2006-10-06 10:19   ` Agustin Martin
  0 siblings, 1 reply; 3+ messages in thread
From: Richard Stallman @ 2006-10-01 22:25 UTC (permalink / raw)
  Cc: emacs-devel

It looks good at first read, but I don't have a printer and I find
it hard to really study it.  Anyway, since this is to support
a peculiar mode of operation, let's put it off until after
the release.

^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: {ispell,flyspell}.el and coexistence of ispell and aspell
  2006-10-01 22:25 ` Richard Stallman
@ 2006-10-06 10:19   ` Agustin Martin
  0 siblings, 0 replies; 3+ messages in thread
From: Agustin Martin @ 2006-10-06 10:19 UTC (permalink / raw)


[-- Attachment #1: Type: text/plain, Size: 1791 bytes --]

On Sun, Oct 01, 2006 at 06:25:47PM -0400, Richard Stallman wrote:
> It looks good at first read, but I don't have a printer and I find
> it hard to really study it.  Anyway, since this is to support
> a peculiar mode of operation, let's put it off until after
> the release.

OK, 

I am attaching ispell.el patch with fixed docstrings and re-attaching
flyspell patch (small). I am also adding proposed changelog entries, so
everything is kept in the same mail and can be later retrieved after the
release.

In the meantime comments are welcome.

--------------------------------------------------------
flyspell.el:
(flyspell-large-region), (flyspell-mode)
   Call (ispell-initialize-program-params) instead of (ispell-check-version)
   and (ispell-maybe-find-aspell-dictionaries)

ispell.el:
(ispell-initialize-program-params)
   New function. Set value for ispell-dictionary-alist to the base or the
   aspell one as appropriate. Kill ispell process if ispell-program-name is
   changed.
(ispell-last-program-name) 
   Used by the above function.
(ispell-base-dictionary-alist)
   Formerly (ispell-dictionary-alist) 
(ispell-aspell-dictionary-alist)
   New alist for aspell specific values
(ispell-dictionary-alist)
   Set to (ispell-base-dictionary-alist) or (ispell-aspell-dictionary-alist)
   from (ispell-initialize-program-params)
(ispell-have-aspell-dictionaries), (ispell-maybe-find-aspell-dictionaries)
   Removed, obsolete
(ispell-find-aspell-dictionaries)
   Modified to use (ispell-base-dictionary-alist) and set
   (ispell-aspell-dictionary-alist)
(ispell-valid-dictionary-list), (ispell-word), (ispell-region)
   Use (ispell-initialize-program-params) instead of
   (ispell-maybe-find-aspell-dictionaries)
--------------------------------------------------------

-- 
Agustin

[-- Attachment #2: flyspell.el_ispell-initialize-program-params.diff --]
[-- Type: text/plain, Size: 836 bytes --]

--- flyspell.el.orig	2006-09-14 14:57:12.000000000 +0200
+++ flyspell.el	2006-09-14 14:57:26.000000000 +0200
@@ -556,7 +556,7 @@
 ;;*---------------------------------------------------------------------*/
 (defun flyspell-mode-on ()
   "Turn Flyspell mode on.  Do not use this; use `flyspell-mode' instead."
-  (ispell-maybe-find-aspell-dictionaries)
+  (ispell-initialize-program-params)
   (setq ispell-highlight-face 'flyspell-incorrect)
   ;; local dictionaries setup
   (or ispell-local-dictionary ispell-dictionary
@@ -1476,7 +1476,7 @@
     ;; this is done, we can start checking...
     (if flyspell-issue-message-flag (message "Checking region..."))
     (set-buffer curbuf)
-    (ispell-check-version)
+    (ispell-initialize-program-params)
     (let ((c (apply 'call-process-region beg
 		    end
 		    ispell-program-name

[-- Attachment #3: ispell.el_ispell-initialize-program-params.diff2 --]
[-- Type: text/plain, Size: 5674 bytes --]

--- ispell.el.orig	2006-09-14 14:59:04.000000000 +0200
+++ ispell.el	2006-10-04 11:08:08.000000000 +0200
@@ -659,11 +659,11 @@
 
 
 ;;;###autoload
-(defvar ispell-dictionary-alist
+(defvar ispell-base-dictionary-alist
   (append ispell-dictionary-alist-1 ispell-dictionary-alist-2
 	  ispell-dictionary-alist-3 ispell-dictionary-alist-4
 	  ispell-dictionary-alist-5 ispell-dictionary-alist-6)
-  "An alist of dictionaries and their associated parameters.
+  "Base alist of dictionaries and their associated parameters.
 
 Each element of this list is also a list:
 
@@ -716,6 +716,14 @@
 contain the same character set as casechars and otherchars in the
 LANGUAGE.aff file \(e.g., english.aff\).")
 
+;;;###autoload
+(defvar ispell-dictionary-alist ispell-base-dictionary-alist
+  "Runtime alist of dictionaries and their associated parameters.
+This alist will be modified to match current spellchecker.")
+
+(defvar ispell-aspell-dictionary-alist nil
+  "Parsed alist of aspell dicts and their associated parameters.")
+
 (defvar ispell-really-aspell nil) ; Non-nil if aspell extensions should be used
 
 (defvar ispell-aspell-supports-utf8 nil
@@ -725,8 +733,6 @@
 Earlier aspell versions do not consistently support UTF-8.  Handling
 this would require some extra guessing in `ispell-aspell-find-dictionary'.")
 
-
-
 ;;; **********************************************************************
 ;;; The following are used by ispell, and should not be changed.
 ;;; **********************************************************************
@@ -876,18 +882,29 @@
 
 ;; Make ispell.el work better with aspell.
 
-(defvar ispell-have-aspell-dictionaries nil
-  "Non-nil if we have queried Aspell for dictionaries at least once.")
+(defvar ispell-last-program-name nil
+  "`ispell-program-name' value used in last spellchecking command.")
 
-(defun ispell-maybe-find-aspell-dictionaries ()
-  "Find Aspell's dictionaries, unless already done."
-  (when (and (not ispell-have-aspell-dictionaries)
-	     (condition-case ()
-		 (progn (ispell-check-version) t)
+(defun ispell-initialize-program-params ( &optional force )
+  "Set right alist of dict params for current spellchecker.
+This will be run if not yet done or `ispell-program-name' is
+changed. FORCE will run this unconditionally"
+  (when (or (not (eq ispell-last-program-name ispell-program-name))
+	    force)
+    (ispell-kill-ispell t)
+    (if (and (condition-case ()
+		 (progn
+		   (setq ispell-library-directory (ispell-check-version))
+		   t)
 	       (error nil))
 	     ispell-really-aspell
 	     ispell-aspell-supports-utf8)
-    (ispell-find-aspell-dictionaries)))
+	(progn
+	  (if (not ispell-aspell-dictionary-alist)
+	      (ispell-find-aspell-dictionaries))
+	  (setq ispell-dictionary-alist ispell-aspell-dictionary-alist))
+      (setq ispell-dictionary-alist ispell-base-dictionary-alist))
+    (setq ispell-last-program-name ispell-program-name)))
 
 (defun ispell-find-aspell-dictionaries ()
   "Find Aspell's dictionaries, and record in `ispell-dictionary-alist'."
@@ -907,17 +924,16 @@
     (setq found (ispell-aspell-add-aliases found))
     ;; Merge into FOUND any elements from the standard ispell-dictionary-alist
     ;; which have no element in FOUND at all.    
-    (dolist (dict ispell-dictionary-alist)
+    (dolist (dict ispell-base-dictionary-alist)
       (unless (assoc (car dict) found)
 	(setq found (nconc found (list dict)))))
-    (setq ispell-dictionary-alist found)
+    (setq ispell-aspell-dictionary-alist found)
     ;; Add a default entry
-    (let* ((english-dict (assoc "en" ispell-dictionary-alist))
+    (let* ((english-dict (assoc "en" ispell-aspell-dictionary-alist))
 	   (default-dict
 	     (cons nil (or (cdr english-dict)
 			   (cdr (car ispell-dictionary-alist-1))))))
-      (push default-dict ispell-dictionary-alist))
-    (setq ispell-have-aspell-dictionaries t)))
+      (push default-dict ispell-aspell-dictionary-alist))))
 
 (defvar ispell-aspell-data-dir nil
   "Data directory of Aspell.")
@@ -1002,8 +1018,8 @@
 (defun ispell-valid-dictionary-list ()
   "Returns a list of valid dictionaries.
 The variable `ispell-library-directory' defines the library location."
-  ;; If Ispell is really Aspell, query it for the dictionary list.
-  (ispell-maybe-find-aspell-dictionaries)
+  ;; Make sure ispell program is initialized (right dicts lists, paths, ...)
+  (ispell-initialize-program-params)
   (let ((dicts (append ispell-local-dictionary-alist ispell-dictionary-alist))
 	(dict-list (cons "default" nil))
 	name load-dict)
@@ -1582,7 +1598,7 @@
   (interactive (list ispell-following-word ispell-quietly current-prefix-arg))
   (if continue
       (ispell-continue)
-    (ispell-maybe-find-aspell-dictionaries)
+    (ispell-initialize-program-params)
     (ispell-accept-buffer-local-defs)	; use the correct dictionary
     (let ((cursor-location (point))	; retain cursor location
 	  (word (ispell-get-word following))
@@ -2600,6 +2616,7 @@
 Without a prefix arg, set it \"locally\", just for this buffer.
 
 By just answering RET you can find out what the current dictionary is."
+  (ispell-initialize-program-params)
   (interactive
    (list (completing-read
 	  "Use new dictionary (RET for current, SPC to complete): "
@@ -2656,7 +2673,7 @@
 Return nil if spell session is quit,
  otherwise returns shift offset amount for last line processed."
   (interactive "r")			; Don't flag errors on read-only bufs.
-  (ispell-maybe-find-aspell-dictionaries)
+  (ispell-initialize-program-params)
   (if (not recheckp)
       (ispell-accept-buffer-local-defs)) ; set up dictionary, local words, etc.
   (let ((skip-region-start (make-marker))

[-- Attachment #4: Type: text/plain, Size: 142 bytes --]

_______________________________________________
Emacs-devel mailing list
Emacs-devel@gnu.org
http://lists.gnu.org/mailman/listinfo/emacs-devel

^ permalink raw reply	[flat|nested] 3+ messages in thread

end of thread, other threads:[~2006-10-06 10:19 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2006-09-28 10:06 {ispell,flyspell}.el and coexistence of ispell and aspell Agustin Martin
2006-10-01 22:25 ` Richard Stallman
2006-10-06 10:19   ` Agustin Martin

Code repositories for project(s) associated with this public inbox

	https://git.savannah.gnu.org/cgit/emacs.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).