Back to index

im-sdk  12.3.91
newpinyin_interface.c
Go to the documentation of this file.
00001 #include <stdio.h>
00002 #include "newpinyin_im.h"
00003 
00004 #define NEWPINYIN_VERSION   202
00005 #define NEWPINYIN_NAME_UTF8 "NewPinYin"
00006 #define NEWPINYIN_UUID             "newpinyin-9d3878a2-ca6a-4dbb-9e81-62b3774716c3"
00007 #define NEWPINYIN_AUTHOR    "Ervin Yan <Ervin.Yan@sun.com>"
00008 #define NEWPINYIN_COPYRIGHT "Copyright (c) 2005 Sun Microsystems"
00009 #define NEWPINYIN_HINTING   "NewPinYin Input Method"
00010 #define NEWPINYIN_ICONPATH  "newpinyin.xpm"
00011 
00012 #define NEWSHUANGPIN_UUID   "newshuangpin-6ab65f44-a765-4303-87d5-5d1a0d22f96d"
00013 #define NEWSHUANGPIN_ICONPATH      "newshuangpin.xpm"
00014 
00015 ImeResult newpinyin_Initialize(ImeInfo ime_info);
00016 ImeResult newpinyin_Destroy(ImeInfo ime_info);
00017 ImeResult newpinyin_Process_Key_Event(ImeInputContext ic, ImeKey key_event);
00018 ImeResult newpinyin_Create_Session(ImeInputContext ic);
00019 ImeResult newpinyin_Destroy_Session(ImeInputContext ic);
00020 ImeResult newpinyin_FocusIn(ImeInputContext ic);
00021 ImeResult newpinyin_FocusOut(ImeInputContext ic);
00022 
00023 ImmServices imm_services;
00024 
00025 #define MAX_SESSIONS 1024
00026 
00027 typedef struct _newpinyin_im_data_t {
00028        int   encoding;
00029        char  opened_session[MAX_SESSIONS];
00030 } newpinyin_im_data_t;
00031 
00032 ImeMethodsRec newpinyin_methods = {
00033        1,                                /* version */
00034        newpinyin_Initialize,             /* ImeInitialize */
00035        newpinyin_Destroy,                /* ImeDestroy  */
00036        newpinyin_Process_Key_Event,      /* ImeProcessKeyEvent */
00037        NULL,                             /* ImeProcessAuxEvent  */
00038        newpinyin_Create_Session,         /* ImeAttachSession */
00039        newpinyin_Destroy_Session,        /* ImeDetachSession */
00040        newpinyin_FocusIn,                             /* ImeFocusIn  */
00041        newpinyin_FocusOut,                             /* ImeFocusOut */
00042        NULL,                             /* ImeAttachUser */
00043        NULL,                             /* ImeDetachUser */
00044        NULL,                             /* ImeAttachDesktop */
00045        NULL,                             /* ImeDetachDesktop */
00046        NULL,                             /* ImeGetErrorMessage */
00047 #if 0
00048        NULL,                             /* ImeDoConfig */
00049 #endif
00050 };
00051 
00052 #ifdef WIN32
00053 #define EXPORT extern __declspec(dllexport)
00054 EXPORT
00055 #endif
00056 ImeResult RegisterIME(ImmServices srvs, ImeInfo* ppinfo, ImeMethods* pmthds, int argc, char **argv)
00057 {
00058        ImeInfoRec *newpinyin_info = NULL;
00059        int  encoding = ENCODE_GB2312;
00060        char *encoding_str = NULL;
00061        char *base_dir = NULL;
00062        newpinyin_im_data_t *newpinyin_data = NULL;
00063 
00064        int i, ret;
00065 
00066        DEBUG_printf("Register NewPinYin IM: argc: %d\n", argc);
00067        for (i=0; i<argc; i++) {
00068               if (!strcasecmp(argv[i], "-basedir")) {
00069                      if (argv[i+1]) {
00070                             base_dir = argv[i+1];
00071                             DEBUG_printf("       setting base dir to: %s\n", argv[i+1]);
00072                      }
00073                      i++;
00074               } else if (!strcasecmp(argv[i], "-encoding")) {
00075                      if (argv[i+1]) {
00076                             encoding_str = argv[i+1];
00077                             DEBUG_printf("       setting newpinyin file to: %s\n", argv[i+1]);
00078                      }
00079                      i++;
00080               }
00081        }
00082 
00083        if (encoding_str && *encoding_str) {
00084               if (!strcasecmp(encoding_str, "gb2312"))
00085                      encoding = ENCODE_GB2312;
00086               else if (!strcasecmp(encoding_str, "gbk"))
00087                      encoding = ENCODE_GBK;
00088        }
00089 
00090        newpinyin_info = (ImeInfoRec *)calloc(1, sizeof(ImeInfoRec));
00091        DEBUG_printf("newpinyin_info: 0x%x\n", newpinyin_info);
00092        if (newpinyin_info == NULL)  {
00093               return (IME_FAIL);
00094        }
00095        
00096        DEBUG_printf("get newpinyin_im_data_t\n");
00097        newpinyin_data = (newpinyin_im_data_t *)calloc(1, sizeof(newpinyin_im_data_t));
00098        DEBUG_printf("newpinyin_data: 0x%x\n", newpinyin_data);
00099        if (newpinyin_data == NULL) {
00100               free ((char *)newpinyin_info);
00101               return (IME_FAIL);
00102        }
00103 
00104        newpinyin_info->version           = NEWPINYIN_VERSION;
00105 #ifdef CompByNewPinyin
00106        newpinyin_info->name              = "ȫƴ";
00107        newpinyin_info->uuid          = NEWPINYIN_UUID;
00108        newpinyin_info->icon_file         = NEWPINYIN_ICONPATH;
00109 #else
00110        newpinyin_info->name              = "˫ƴ";
00111        newpinyin_info->uuid          = NEWSHUANGPIN_UUID;
00112        newpinyin_info->icon_file         = NEWSHUANGPIN_ICONPATH;
00113 #endif
00114        newpinyin_info->encoding          = encoding;
00115        newpinyin_info->author            = NEWPINYIN_AUTHOR;
00116        newpinyin_info->hinting           = NEWPINYIN_HINTING;
00117        newpinyin_info->copyright         = NEWPINYIN_COPYRIGHT;
00118        newpinyin_info->support_locales = "zh_CN.UTF-8,zh_CN.GB18030";
00119 
00120        newpinyin_data->encoding = encoding;
00121        for (i=0; i<MAX_SESSIONS; i++) {
00122               newpinyin_data->opened_session[i] = 0;
00123        }
00124        newpinyin_data->opened_session[0] = 1;
00125        newpy_open(0);
00126 
00127        newpinyin_info->specific_data     = (void *)newpinyin_data;
00128 
00129        *ppinfo = newpinyin_info;
00130        *pmthds = &newpinyin_methods;
00131 
00132        imm_services = srvs;
00133 
00134        DEBUG_printf("begin leave Register IME\n");
00135        return (IME_OK);
00136 }
00137 
00138 ImeResult newpinyin_Initialize(ImeInfo newpinyin_info)
00139 {
00140        int ret;
00141 
00142        DEBUG_printf("newpinyin_Initialize\n");
00143 
00144 /*
00145        ret = newpy_open(0);
00146        if (ret == -1)
00147               return(IME_FAIL);
00148 */
00149 
00150        return (IME_OK);
00151 }
00152 
00153 ImeResult newpinyin_Destroy(ImeInfo newpinyin_info)
00154 {
00155        int i;
00156        newpinyin_im_data_t *newpinyin_data;
00157 
00158        DEBUG_printf("newpinyin_Destroy\n");
00159 
00160        if (newpinyin_info != NULL) {
00161               newpinyin_data = (newpinyin_im_data_t *)newpinyin_info->specific_data;
00162               if (newpinyin_data) {
00163                      for (i=0; i<MAX_SESSIONS; i++) {
00164                             if (newpinyin_data->opened_session[i] == 1)
00165                                    newpy_close(i);
00166                      }
00167 
00168                      free ((char *)newpinyin_data);
00169               }
00170 
00171               free ((char *)newpinyin_info);
00172        }
00173 
00174        return (IME_OK);
00175 }
00176 
00177 ImeResult newpinyin_Create_Session(ImeInputContext ic)
00178 {
00179        int i, ret;
00180        ImmResult imm_result;
00181        ImeBufferRec *ime_buffer = NULL;
00182        ImeInfoRec *newpinyin_info = NULL;
00183        newpinyin_im_data_t *newpinyin_data;
00184 
00185        DEBUG_printf("newpinyin_Create_Session \n");
00186        newpinyin_info = (ImeInfo)imm_services->ImmGetImeInfo(ic);
00187        DEBUG_printf("newpinyin_info: 0x%x\n", newpinyin_info);
00188        if (newpinyin_info == NULL || newpinyin_info->specific_data == NULL)
00189               return (IME_FAIL);
00190 
00191        newpinyin_data = (newpinyin_im_data_t *)newpinyin_info->specific_data;
00192        DEBUG_printf("newpinyin_data: 0x%x\n", newpinyin_data);
00193        if (newpinyin_data == NULL)
00194               return (IME_FAIL);
00195 
00196        ime_buffer = (ImeBufferRec *)imm_services->ImmGetData(ic, IME_SCOPE_SESSION);
00197        DEBUG_printf("newpinyin_Create_Session ======= begin get ime_session_data: 0x%x\n", ime_buffer);
00198        if (ime_buffer == NULL) {
00199               ime_buffer = (ImeBufferRec *)calloc(1, sizeof(ImeBufferRec));
00200               if (ime_buffer == NULL)
00201                      return (IME_FAIL);
00202 
00203               for (i = 0; i < MAX_CANDIDATES_NUM; i++) {
00204                      ime_buffer->candidates[i] = ime_buffer->candidates_buf[i];
00205                      ime_buffer->comments[i] = ime_buffer->comments_buf[i];
00206                      ime_buffer->lookups[i] = ime_buffer->lookups_buf[i];
00207               }
00208 
00209               imm_result = imm_services->ImmSetData(ic, IME_SCOPE_SESSION, ime_buffer);
00210               if (imm_result == IMM_FAIL) {
00211                      free ((char *)ime_buffer);
00212                      return (IME_FAIL);
00213               }
00214        }
00215        
00216        ime_buffer->session_id = 0;
00217        for (i = 0; i < MAX_SESSIONS; i++) {
00218               if (newpinyin_data->opened_session[i] == 0) {
00219                      DEBUG_printf("newpinyin_Create_Session ======= begin newpy_open: %d\n", i);
00220                      ret = newpy_open(i);
00221                      if (ret == -1)
00222                             return (IME_FAIL);
00223                      ime_buffer->session_id = i;
00224                      newpinyin_data->opened_session[i] = 1;
00225                      break;
00226               }
00227        }
00228        return (IME_OK);
00229 }
00230 
00231 ImeResult newpinyin_Destroy_Session(ImeInputContext ic)
00232 {
00233        ImeBufferRec *ime_buffer = NULL;
00234        ImeInfoRec *newpinyin_info = NULL;
00235        newpinyin_im_data_t *newpinyin_data;
00236 
00237        newpinyin_info = (ImeInfo)imm_services->ImmGetImeInfo(ic);
00238        if (newpinyin_info == NULL || newpinyin_info->specific_data == NULL)
00239               return (IME_FAIL);
00240 
00241        newpinyin_data = (newpinyin_im_data_t *)newpinyin_info->specific_data;
00242        if (newpinyin_data == NULL)
00243               return (IME_FAIL);
00244 
00245        ime_buffer = (ImeBufferRec *)imm_services->ImmGetData(ic, IME_SCOPE_SESSION);
00246        DEBUG_printf("newpinyin_Destroy_Session ======= begin get ime_session_data: 0x%x\n", ime_buffer);
00247 
00248        if (ime_buffer != NULL) {
00249               DEBUG_printf("newpinyin_Destroy_Session ======= session_id: 0x%x\n", ime_buffer->session_id);
00250               newpy_close(ime_buffer->session_id);
00251               newpinyin_data->opened_session[ime_buffer->session_id] = 0;
00252               free ((char *)ime_buffer);
00253        }
00254 
00255        imm_services->ImmSetData(ic, IME_SCOPE_SESSION, NULL);
00256 
00257        return (IME_OK);
00258 }
00259 
00260 ImeResult newpinyin_FocusIn(ImeInputContext ic)
00261 {
00262         DEBUG_printf("newpinyin: call newpinyin_FocusIn()\n");
00263         return(IME_OK);
00264 }
00265 
00266 ImeResult newpinyin_FocusOut(ImeInputContext ic)
00267 {
00268         DEBUG_printf("newpinyin: call newpinyin_FocusOut()\n");
00269         return(IME_OK);
00270 }
00271 
00272 ImmResult newpinyin_beep(ImeInputContext ic)
00273 {
00274        return (imm_services->ImmBeep(ic, ImeBeepWarning));
00275 }
00276 
00277 ImmResult newpinyin_commit(ImeInputContext ic, int encoding, char *commit_buf, int commit_len)
00278 {
00279        if (commit_len <= 0)
00280               return (IMM_FAIL);
00281 
00282        if (commit_buf == NULL)
00283               return (IMM_FAIL);
00284 
00285        return (imm_services->ImmCommit(ic, commit_buf));
00286 }
00287 
00288 ImmResult newpinyin_update_preedit(ImeInputContext ic, int encoding,
00289                                char *preedit_buf, int preedit_len, int caret_pos)
00290 {
00291        ImePreeditRec ime_preedit;
00292 
00293        memset(&ime_preedit, 0, sizeof(ImePreeditRec));
00294        if (preedit_len == 0) {
00295               return (imm_services->ImmHidePreedit(ic));
00296        }
00297 
00298        imm_services->ImmShowPreedit(ic);
00299 
00300        ime_preedit.caret = caret_pos;
00301        ime_preedit.preedit.text     = preedit_buf;
00302 
00303        return (imm_services->ImmUpdatePreedit(ic, &ime_preedit));
00304 }
00305 
00306 ImmResult newpinyin_update_candidates(ImeInputContext ic, int encoding, char **candidates, int num_candidates)
00307 {
00308        int i;
00309        ImmResult imm_result;
00310        ImeCandidatesRec       ime_candidates;
00311 
00312        memset(&ime_candidates, 0, sizeof(ImeCandidatesRec));
00313 
00314         ime_candidates.horizental = 0;
00315        
00316        if (num_candidates == 0 || candidates == NULL) {
00317               return (imm_services->ImmHideCandidates(ic));
00318        }
00319 
00320        imm_services->ImmShowCandidates(ic);
00321 
00322        ime_candidates.title = NULL;
00323         ime_candidates.numbers = NULL;
00324        ime_candidates.focus = 0;
00325        ime_candidates.count = num_candidates;
00326        ime_candidates.candidates = (ImeTextRec *)calloc(num_candidates, sizeof(ImeTextRec));
00327        if (ime_candidates.candidates == NULL)
00328               return (IMM_FAIL);
00329 
00330        for (i=0; i<num_candidates; i++) {
00331               ime_candidates.candidates[i].text = candidates[i];
00332        }
00333 
00334        imm_result = imm_services->ImmUpdateCandidates(ic, &ime_candidates);
00335 
00336        free ((char *) ime_candidates.candidates);
00337        return(imm_result);
00338 
00339 }
00340 
00341 /* process key input event */
00342 /* return value:  IME_UNUSED_KEY:  if IME not use this key, return this key to systerm directly */
00343 /*                IME_KEY_USED:      if IME has used this key */
00344 ImeResult newpinyin_Process_Key_Event(ImeInputContext ic, ImeKey key_event)
00345 {
00346        ImeInfoRec *newpinyin_info = NULL;
00347        newpinyin_im_data_t *newpinyin_data;
00348        ImeBufferRec *ime_buffer = NULL;
00349        long    kcode, kstate;
00350        unsigned short kchar;
00351        int ret;
00352 
00353        DEBUG_printf("newpinyin_Process_Key_Event: ic: 0x%x\n", ic);
00354        ime_buffer = (ImeBufferRec *)imm_services->ImmGetData(ic, IME_SCOPE_SESSION);
00355        if (ime_buffer == NULL)
00356               return (IME_UNUSED_KEY);
00357 
00358        DEBUG_printf("newpinyin_Process_Key_Event ======= begin get ime_session_data: 0x%x\n", ime_buffer);
00359        newpinyin_info = (ImeInfo)imm_services->ImmGetImeInfo(ic);
00360        if (newpinyin_info == NULL || newpinyin_info->specific_data == NULL)
00361               return (IME_UNUSED_KEY);
00362 
00363        newpinyin_data = (newpinyin_im_data_t *)newpinyin_info->specific_data;
00364        if (newpinyin_data == NULL)
00365               return (IME_UNUSED_KEY);
00366 
00367        ime_buffer->encoding = newpinyin_data->encoding;
00368 
00369        kcode = key_event->keycode;
00370        kchar = key_event->keychar;
00371        kstate = key_event->modifier;
00372 
00373        DEBUG_printf("Before Modify:keycode:0x%x, keychar:0x%x, keystatus:0x%x\n", kcode, kchar, kstate);
00374        modifyEvent(&kcode, &kchar, &kstate);
00375        DEBUG_printf("After Modify: keycode:0x%x, keychar:0x%x, keystatus:0x%x\n", kcode, kchar, kstate);
00376        ret = newpy_filter(kcode, kchar, kstate, ime_buffer);
00377        DEBUG_printf("After newpy_filter: ret=%d, return_status: 0x%x\n", ret, ime_buffer->return_status);
00378 
00379        if (ime_buffer->return_status & IME_PREEDIT_AREA) {
00380               newpinyin_update_preedit(ic, ime_buffer->encoding, ime_buffer->preedit_buf,
00381                                     ime_buffer->preedit_len, ime_buffer->preedit_caretpos);
00382        }
00383 
00384        if (ime_buffer->return_status & IME_LOOKUP_AREA) {
00385               newpinyin_update_candidates(ic, ime_buffer->encoding, ime_buffer->lookups, ime_buffer->num_candidates);
00386        }
00387        
00388        if (ime_buffer->return_status & IME_COMMIT) {
00389               newpinyin_commit(ic, ime_buffer->encoding, ime_buffer->commit_buf, ime_buffer->commit_len);
00390        }
00391 
00392        if (ret == IME_UNUSED_KEY)
00393               return (IME_UNUSED_KEY);
00394        
00395        return (IME_OK);
00396 }