Back to index

texmacs  1.0.7.15
mac_spellservice.mm
Go to the documentation of this file.
00001 
00002 /******************************************************************************
00003 * MODULE     : mac_spellservice.mm
00004 * DESCRIPTION: interface with the MacOSX standard spell service
00005 * COPYRIGHT  : (C) 2009  Massimiliano Gubinelli
00006 *******************************************************************************
00007 * This software falls under the GNU general public license version 3 or later.
00008 * It comes WITHOUT ANY WARRANTY WHATSOEVER. For details, see the file LICENSE
00009 * in the root directory or <http://www.gnu.org/licenses/gpl-3.0.html>.
00010 ******************************************************************************/
00011 
00012 
00013 #include "MacOS/mac_spellservice.h"
00014 #include "converter.hpp"
00015 #include "language.hpp"
00016 
00017 #include "Cocoa/mac_cocoa.h"
00018 
00019 static string 
00020 from_nsstring (NSString *s) {
00021   const char *cstr = [s cStringUsingEncoding:NSUTF8StringEncoding];
00022   return utf8_to_cork(string((char*)cstr));
00023 }
00024 
00025 
00026 static NSString *
00027 to_nsstring_utf8 (string s) {
00028   s= cork_to_utf8 (s);
00029   char *p = as_charp(s);
00030   NSString *nss = [NSString stringWithCString:p encoding:NSUTF8StringEncoding];
00031   tm_delete_array (p);      
00032   return nss;
00033 }
00034 
00035 
00036 /******************************************************************************
00037 * Dictionaries
00038 ******************************************************************************/
00039 
00040 static hashmap<string,string> available_dicts ("");
00041 static string current_lang = "";
00042 static NSInteger current_tag = 0;
00043 
00044 static bool mac_spelling_language(string lang)
00045 {
00046   if (available_dicts->contains (lang)) {
00047     current_lang = lang;
00048     [[NSSpellChecker sharedSpellChecker]  setLanguage: to_nsstring_utf8(available_dicts(lang))];
00049     if (DEBUG_EVENTS) cout << "setting lang:"  << lang << LF;
00050     return true;
00051     }
00052   return false;
00053 }
00054 
00055 void
00056 mac_init_dictionary () {
00057   if (N(available_dicts) == 0) {
00058     hashmap<string,string> the_dicts ("");
00059 
00060     //FIXME: Complete dictionary list
00061     the_dicts("en") = "english";
00062     the_dicts("fr") = "french";
00063     the_dicts("it") = "italian";
00064 
00065     NSArray *arr = [[NSSpellChecker sharedSpellChecker] availableLanguages];
00066     NSEnumerator *enumerator = [arr objectEnumerator];
00067     NSString *nsdict;
00068     
00069     while ((nsdict = (NSString*)[enumerator nextObject])) {
00070       string dict = from_nsstring(nsdict);
00071 //      available_dicts(the_dicts(dict)) = dict;
00072       available_dicts (locale_to_language (dict)) = dict;
00073     }
00074   }
00075 }
00076 
00077 
00078 /******************************************************************************
00079 * Spell checking interface
00080 ******************************************************************************/
00081 
00082 
00083 string
00084 mac_spell_start (string lan) {
00085   string r;
00086   NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
00087   // we need to be sure that the Cocoa application infrastructure is initialized 
00088   // (apparently Qt does not do this properly and the NSSpellChecker instance returns null
00089   //  without the following instruction)
00090   NSApplication *NSApp=[NSApplication sharedApplication]; (void) NSApp;
00091   mac_init_dictionary ();
00092   if (mac_spelling_language (lan)) {
00093     // warning: we must be sure that the tag is relased by the appropriate message to sharedSpellChecker
00094     current_tag = [NSSpellChecker uniqueSpellDocumentTag];
00095     r = "ok";
00096   } else {
00097     r = "Error: no dictionary for#" * lan;
00098   }  
00099   [pool release];
00100   return r;
00101 }
00102 
00103 tree
00104 mac_spell_check (string lan, string s) {
00105   if (DEBUG_EVENTS) cout << "spell_check " << lan << " :: " << s << LF;
00106   tree t;
00107   NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
00108   if ((lan != current_lang) && (! mac_spelling_language (lan))) {
00109       t = "Error: dictionary not available";
00110   } else {
00111     NSString *nss = to_nsstring_utf8 (s);
00112     NSRange r =  [[NSSpellChecker sharedSpellChecker]  
00113                   checkSpellingOfString: nss
00114                   startingAt: 0
00115                   language: nil
00116                   wrap: NO
00117                   inSpellDocumentWithTag: current_tag
00118                   wordCount: NULL];
00119     if (r.length == 0) 
00120       t = "ok";
00121     else {
00122       NSArray *arr = [[NSSpellChecker sharedSpellChecker] guessesForWord: nss];
00123       if ([arr count] == 0) {
00124         t = tree (TUPLE, "0");
00125       } else {
00126         NSEnumerator *enumerator = [arr objectEnumerator];
00127         NSString *sugg;
00128         tree a (TUPLE);
00129         while ((sugg = (NSString*)[enumerator nextObject])) {
00130           a << from_nsstring (sugg);
00131         }
00132         t= tree (TUPLE, as_string((int)[arr count]));
00133         t << A (a);        
00134       }
00135     }
00136   }
00137   [pool release];
00138 
00139   if (DEBUG_EVENTS)   cout << t << LF;     
00140   return t;
00141 }
00142 
00143 void
00144 mac_spell_accept (string lan, string s) {
00145   NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
00146   if ((lan != current_lang) && (! mac_spelling_language (lan))) {
00147     // do nothing
00148     ;
00149   } else {
00150     [[NSSpellChecker sharedSpellChecker]  ignoreWord:to_nsstring_utf8 (s) inSpellDocumentWithTag:current_tag];
00151   }  
00152   //  ispell_send (lan, "@" * s);
00153   [pool release];
00154 }
00155 
00156 void
00157 mac_spell_insert (string lan, string s) {
00158   NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
00159   if ((lan != current_lang) && (! mac_spelling_language (lan))) {
00160     // do nothing
00161     ;
00162   } else {
00163     [[NSSpellChecker sharedSpellChecker] learnWord:to_nsstring_utf8 (s)];
00164   }  
00165   //  ispell_send (lan, "*" * s);
00166   [pool release];
00167 }
00168 
00169 void
00170 mac_spell_done (string lan) {
00171   (void) lan;
00172   NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
00173   [[NSSpellChecker sharedSpellChecker] closeSpellDocumentWithTag:current_tag];
00174   current_tag = 0;
00175   [pool release];
00176 }
00177