Back to index

im-sdk  12.3.91
iiimpICS.c
Go to the documentation of this file.
00001 /*
00002 Copyright 1990-2001 Sun Microsystems, Inc. All Rights Reserved.
00003 
00004 Permission is hereby granted, free of charge, to any person obtaining a
00005 copy of this software and associated documentation files (the
00006 "Software"), to deal in the Software without restriction, including
00007 without limitation the rights to use, copy, modify, merge, publish,
00008 distribute, sublicense, and/or sell copies of the Software, and to
00009 permit persons to whom the Software is furnished to do so, subject to
00010 the following conditions: The above copyright notice and this
00011 permission notice shall be included in all copies or substantial
00012 portions of the Software.
00013 
00014 
00015 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
00016 OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
00017 MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
00018 IN NO EVENT SHALL THE OPEN GROUP OR SUN MICROSYSTEMS, INC. BE LIABLE
00019 FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
00020 CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH
00021 THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE EVEN IF
00022 ADVISED IN ADVANCE OF THE POSSIBILITY OF SUCH DAMAGES.
00023 
00024 
00025 Except as contained in this notice, the names of The Open Group and/or
00026 Sun Microsystems, Inc. shall not be used in advertising or otherwise to
00027 promote the sale, use or other dealings in this Software without prior
00028 written authorization from The Open Group and/or Sun Microsystems,
00029 Inc., as applicable.
00030 
00031 
00032 X Window System is a trademark of The Open Group
00033 
00034 OSF/1, OSF/Motif and Motif are registered trademarks, and OSF, the OSF
00035 logo, LBX, X Window System, and Xinerama are trademarks of the Open
00036 Group. All other trademarks and registered trademarks mentioned herein
00037 are the property of their respective owners. No right, title or
00038 interest in or to any trademark, service mark, logo or trade name of
00039 Sun Microsystems, Inc. or its licensors is granted.
00040 
00041 */
00042 #include "iiimpIM.h"
00043 #include "switchIM.h"
00044 #include "guiIM.h"
00045 #include "guiIMPre.h"
00046 #include "iiimpICG.h"
00047 #include "XimpIm.h"
00048 #include "trace_message.h"
00049 
00050 extern int SelectCharacterSubset(XicCommon,
00051                              XIMUnicodeCharacterSubset *aSubset);
00052 
00053 typedef enum {
00054   DO_PREEDIT_WIN = (1L << 0),
00055   DO_PREEDIT_MOVE = (1L << 1),
00056   DO_PREEDIT_FONT = (1L << 2),
00057 
00058   DO_STATUS_WIN = (1L << 3),
00059   DO_STATUS_FONT = (1L << 4),
00060 
00061   DO_LOOKUP_MOVE = (1L << 5)
00062 } DoThisAction;
00063 
00064 Bool
00065 PreeditSetAttributes(XicCommon ic, Ximp_PreeditPropRec4 *attr,
00066                    XIMArg *vl, XICSetMode mode,
00067                    XimpChangeaMask change_mask,
00068                    char *return_name) {
00069   XIMArg *p;
00070 
00071   DoThisAction action = 0;
00072 
00073   for (p = vl; p && p->name != NULL; p++) {
00074     TRACE_MESSAGE('a', ("iiimp_PreeditSetAttributes: %s\n", p->name));
00075     if (strcmp(p->name, XNArea)==0) {
00076       ic->core.preedit_attr.area.x = ((XRectangle *)p->value)->x;
00077       ic->core.preedit_attr.area.y = ((XRectangle *)p->value)->y;
00078       ic->core.preedit_attr.area.width = ((XRectangle *)p->value)->width;
00079       ic->core.preedit_attr.area.height = ((XRectangle *)p->value)->height;
00080       if (ic->core.preedit_attr.area.width == 0) {
00081        ic->core.preedit_attr.area.width = GetAreaNeededWidth(ic);
00082       }
00083       if (ic->core.preedit_attr.area.height == 0) {
00084        ic->core.preedit_attr.area.height = GetAreaNeededHeight(ic);
00085       }
00086       attr->Area.x      = ic->core.preedit_attr.area.x;
00087       attr->Area.y      = ic->core.preedit_attr.area.y;
00088       attr->Area.width  = ic->core.preedit_attr.area.width;
00089       attr->Area.height = ic->core.preedit_attr.area.height;
00090       XIMP_SET_PREAREAMASK(ic, change_mask);
00091 
00092       action |= DO_PREEDIT_WIN;
00093 
00094     } else if (strcmp(p->name, XNAreaNeeded)==0) {
00095       ic->core.preedit_attr.area_needed.width
00096        = ((XRectangle *)p->value)->width;
00097       ic->core.preedit_attr.area_needed.height
00098        = ((XRectangle *)p->value)->height;
00099       attr->AreaNeeded.width  = ic->core.preedit_attr.area_needed.width;
00100       attr->AreaNeeded.height = ic->core.preedit_attr.area_needed.height;
00101       XIMP_SET_PREAREANEEDMASK(ic, change_mask);
00102 
00103     } else if (strcmp(p->name, XNSpotLocation)==0) {
00104       ic->core.preedit_attr.spot_location.x = ((XPoint *)p->value)->x;
00105       ic->core.preedit_attr.spot_location.y = ((XPoint *)p->value)->y;
00106       attr->SpotLocation.x = ic->core.preedit_attr.spot_location.x;
00107       attr->SpotLocation.y = ic->core.preedit_attr.spot_location.y;
00108       XIMP_SET_PRESPOTLMASK(ic, change_mask);
00109       XIC_GUI(ic, change_lookup)((XIC)ic, LOOKUP_MOVE, NULL);
00110 
00111       action |= DO_PREEDIT_MOVE | DO_PREEDIT_WIN;
00112 
00113     } else if (strcmp(p->name, XNColormap)==0) {
00114       ic->core.preedit_attr.colormap = (Colormap)p->value;
00115       attr->Colormap = ic->core.preedit_attr.colormap;
00116       XIMP_SET_PRECOLORMAPMASK(ic, change_mask);
00117 
00118     } else if (strcmp(p->name, XNStdColormap)==0) {
00119       XStandardColormap *colormap_ret;
00120       int count;
00121       if (XGetRGBColormaps(ic->core.im->core.display,
00122                         ic->core.focus_window, &colormap_ret,
00123                         &count, (Atom)p->value) != 0) {
00124        ic->core.preedit_attr.std_colormap = (Atom)p->value;
00125        attr->StdColormap = ic->core.preedit_attr.std_colormap;
00126        XIMP_SET_PRESTDCOLORMAPMASK(ic, change_mask);
00127       } else {
00128        return_name = p->name;
00129        return False;
00130       }
00131 
00132     } else if (strcmp(p->name, XNBackground)==0) {
00133       ic->core.preedit_attr.background = (unsigned long)p->value;
00134       attr->Background = ic->core.preedit_attr.background;
00135       XIMP_SET_PREBGMASK(ic, change_mask);
00136       XIC_GUI(ic, change_preedit)((XIC)ic, PREEDIT_BG, NULL);
00137 
00138     } else if (strcmp(p->name, XNForeground)==0) {
00139       ic->core.preedit_attr.foreground = (unsigned long)p->value;
00140       attr->Foreground = ic->core.preedit_attr.foreground;
00141       XIMP_SET_PREFGMASK(ic, change_mask);
00142       XIC_GUI(ic, change_preedit)((XIC)ic, PREEDIT_FG, NULL);
00143 
00144     } else if (strcmp(p->name, XNBackgroundPixmap)==0) {
00145       ic->core.preedit_attr.background_pixmap = (Pixmap)p->value;
00146       attr->Bg_Pixmap = ic->core.preedit_attr.background_pixmap;
00147       XIMP_SET_PREBGPIXMAPMASK(ic, change_mask);
00148 
00149     } else if (strcmp(p->name, XNFontSet)==0) {
00150       if (ic->core.preedit_attr.fontset == (XFontSet)p->value) {
00151        /* same font, no need to set again */
00152        continue;
00153       }
00154       ic->core.preedit_attr.fontset = (XFontSet)p->value;
00155       XIMP_SET_PREFONTMASK(ic, change_mask);
00156 
00157       action |= DO_PREEDIT_FONT | DO_PREEDIT_MOVE | DO_PREEDIT_WIN;
00158 
00159     } else if (strcmp(p->name, XNLineSpace)==0) {
00160       ic->core.preedit_attr.line_spacing = (long)p->value;
00161       attr->LineSpacing = ic->core.preedit_attr.line_spacing;
00162       XIMP_SET_PRELINESPMASK(ic, change_mask);
00163 
00164     } else if (strcmp(p->name, XNCursor)==0) {
00165       ic->core.preedit_attr.cursor = (Cursor)p->value;
00166       attr->Cursor = ic->core.preedit_attr.cursor;
00167       XIMP_SET_PRECURSORMASK(ic, change_mask);
00168 
00169     } else if (strcmp(p->name, XNPreeditStartCallback)==0) {
00170       ic->core.preedit_attr.start_callback.client_data =
00171        ((XIMCallback *)p->value)->client_data;
00172       ic->core.preedit_attr.start_callback.callback =
00173        ((XIMCallback *)p->value)->callback;
00174       ic->ximp_icpart->value_mask |= XIMP_PRE_CALLBAK;
00175 
00176     } else if (strcmp(p->name, XNPreeditDoneCallback)==0) {
00177       ic->core.preedit_attr.done_callback.client_data =
00178        ((XIMCallback *)p->value)->client_data;
00179       ic->core.preedit_attr.done_callback.callback =
00180        ((XIMCallback *)p->value)->callback;
00181       ic->ximp_icpart->value_mask |= XIMP_PRE_CALLBAK;
00182                   
00183     } else if (strcmp(p->name, XNPreeditDrawCallback)==0) {
00184       ic->core.preedit_attr.draw_callback.client_data =
00185        ((XIMCallback *)p->value)->client_data;
00186       ic->core.preedit_attr.draw_callback.callback =
00187        ((XIMCallback *)p->value)->callback;
00188       ic->ximp_icpart->value_mask |= XIMP_PRE_CALLBAK;
00189 
00190     } else if (strcmp(p->name, XNPreeditCaretCallback)==0) {
00191       ic->core.preedit_attr.caret_callback.client_data =
00192        ((XIMCallback *)p->value)->client_data;
00193       ic->core.preedit_attr.caret_callback.callback =
00194        ((XIMCallback *)p->value)->callback;
00195       ic->ximp_icpart->value_mask |= XIMP_PRE_CALLBAK;
00196 /*
00197   4325454: XNPreeditState and XNPreeditStateNotifyCallback should be
00198        handled as PreeditAttribute
00199 */
00200     } else if (strcmp(p->name, XNPreeditState)==0) {
00201       ic->core.preedit_attr.preedit_state = (XIMPreeditState)p->value;
00202       ChangePreeditState(ic);
00203     } else if (strcmp(p->name, XNPreeditStateNotifyCallback)==0) {
00204       ic->core.preedit_attr.state_notify_callback.client_data =
00205        ((XIMCallback *)p->value)->client_data;
00206       ic->core.preedit_attr.state_notify_callback.callback =
00207        ((XIMCallback *)p->value)->callback;
00208       ic->ximp_icpart->value_mask |= XIMP_PRE_CALLBAK;
00209     }
00210   }
00211 
00212   /* do action */
00213   if (action & DO_PREEDIT_WIN)
00214     XIC_GUI(ic, change_preedit)((XIC)ic, PREEDIT_WIN, NULL);
00215   if (action & DO_PREEDIT_FONT)
00216     XIC_GUI(ic, change_preedit)((XIC)ic, PREEDIT_FONT, NULL);
00217   if (action & DO_PREEDIT_MOVE)
00218     XIC_GUI(ic, change_preedit)((XIC)ic, PREEDIT_MOVE, NULL);
00219 
00220   return True;
00221 }
00222 
00223 Bool
00224 StatusSetAttributes(XicCommon ic, Ximp_StatusPropRec4 *attr,
00225                   XIMArg *vl, XICSetMode mode,
00226                   XimpChangeaMask change_mask, char *return_name) {
00227   XIMArg *p;
00228 
00229   for (p = vl; p && p->name != NULL; p++) {
00230     if (strcmp(p->name, XNArea)==0) {
00231       ic->core.status_attr.area.x = ((XRectangle *)p->value)->x;
00232       ic->core.status_attr.area.y = ((XRectangle *)p->value)->y;
00233       ic->core.status_attr.area.width = ((XRectangle *)p->value)->width;
00234       ic->core.status_attr.area.height = ((XRectangle *)p->value)->height;
00235       attr->Area.x      = ic->core.status_attr.area.x;
00236       attr->Area.y      = ic->core.status_attr.area.y;
00237       attr->Area.width  = ic->core.status_attr.area.width;
00238       attr->Area.height = ic->core.status_attr.area.height;
00239       XIMP_SET_STSAREAMASK(ic, change_mask);
00240       XIC_GUI(ic, change_status)((XIC)ic, STATUS_WIN, NULL);
00241 
00242     } else if (strcmp(p->name, XNAreaNeeded)==0) {
00243       ic->core.status_attr.area_needed.width
00244        = ((XRectangle *)p->value)->width;
00245       ic->core.status_attr.area_needed.height
00246        = ((XRectangle *)p->value)->height;
00247       attr->AreaNeeded.width  = ic->core.status_attr.area_needed.width;
00248       attr->AreaNeeded.height = ic->core.status_attr.area_needed.height;
00249       XIMP_SET_STSAREANEEDMASK(ic, change_mask);
00250 
00251     } else if (strcmp(p->name, XNColormap)==0) {
00252       ic->core.status_attr.colormap = (Colormap)p->value;
00253       attr->Colormap = ic->core.status_attr.colormap;
00254       XIMP_SET_STSCOLORMAPMASK(ic, change_mask);
00255 
00256     } else if (strcmp(p->name, XNStdColormap)==0) {
00257       XStandardColormap *colormap_ret;
00258       int count;
00259       if (XGetRGBColormaps(ic->core.im->core.display,
00260                         ic->core.focus_window, &colormap_ret,
00261                         &count, (Atom)p->value) !=0) {
00262        ic->core.status_attr.std_colormap = (Atom)p->value;
00263        attr->StdColormap = ic->core.status_attr.std_colormap;
00264        XIMP_SET_STSSTDCOLORMAPMASK(ic, change_mask);
00265       } else {
00266        return_name = p->name;
00267        return False;
00268       }
00269 
00270     } else if (strcmp(p->name, XNBackground)==0) {
00271       ic->core.status_attr.background = (unsigned long)p->value;
00272       attr->Background = ic->core.status_attr.background;
00273       XIMP_SET_STSBGMASK(ic, change_mask);
00274       XIC_GUI(ic, change_status)((XIC)ic, STATUS_BG, NULL);
00275 
00276     } else if (strcmp(p->name, XNForeground)==0) {
00277       ic->core.status_attr.foreground = (unsigned long)p->value;
00278       attr->Foreground = ic->core.status_attr.foreground;
00279       XIMP_SET_STSFGMASK(ic, change_mask);
00280       XIC_GUI(ic, change_status)((XIC)ic, STATUS_FG, NULL);
00281 
00282     } else if (strcmp(p->name, XNBackgroundPixmap)==0) {
00283       ic->core.status_attr.background_pixmap = (Pixmap)p->value;
00284       attr->Bg_Pixmap = ic->core.status_attr.background_pixmap;
00285       XIMP_SET_STSBGPIXMAPMASK(ic, change_mask);
00286 
00287     } else if (strcmp(p->name, XNFontSet)==0) {
00288       if (ic->core.status_attr.fontset == (XFontSet)p->value) {
00289        /* same font, no need to set again */
00290        continue;
00291       }
00292       ic->core.status_attr.fontset = (XFontSet)p->value;
00293       XIMP_SET_STSFONTMASK(ic, change_mask);
00294       XIC_GUI(ic, change_status)((XIC)ic, STATUS_FONT, NULL);
00295 
00296 #if 0
00297       if (p->value != NULL) {
00298        int list_ret;
00299        XFontStruct **struct_list;
00300        char **name_list;
00301        int i, len;
00302        char *tmp;
00303        if (ic->ximp_icpart->status_font)
00304          Xfree(ic->ximp_icpart->status_font);
00305        list_ret = XFontsOfFontSet(ic->core.status_attr.fontset,
00306                                &struct_list, &name_list);
00307        for(i = 0, len = 0; i < list_ret; i++) {
00308          len += (strlen(name_list[i]) + sizeof(char));
00309        }
00310        if ((tmp = Xmalloc(len + list_ret + sizeof(char))) == NULL){
00311          return_name = p->name;
00312          return False;
00313        }
00314        tmp[0] = NULL;
00315        for(i = 0; i < list_ret; i++) {
00316          strcat(tmp, name_list[i]);
00317          strcat(tmp, ",");
00318        }
00319        tmp[len + i - 1] = NULL;
00320        ic->ximp_icpart->status_font = tmp;
00321       } else {
00322        return_name = p->name;
00323        return False;
00324       }
00325 #endif
00326     } else if (strcmp(p->name, XNLineSpace)==0) {
00327       ic->core.status_attr.line_spacing = (long)p->value;
00328       attr->LineSpacing = ic->core.status_attr.line_spacing;
00329       XIMP_SET_STSLINESPMASK(ic, change_mask);
00330 
00331     } else if (strcmp(p->name, XNCursor)==0) {
00332       ic->core.status_attr.cursor = (Cursor)p->value;
00333       attr->Cursor = ic->core.status_attr.cursor;
00334       XIMP_SET_STSCURSORMASK(ic, change_mask);
00335 
00336     } else if (strcmp(p->name, XNStatusStartCallback)==0) {
00337       ic->core.status_attr.start_callback.client_data =
00338        ((XIMCallback *)p->value)->client_data;
00339       ic->core.status_attr.start_callback.callback =
00340        ((XIMCallback *)p->value)->callback;
00341       ic->ximp_icpart->value_mask |= XIMP_STS_CALLBAK;
00342 
00343     } else if (strcmp(p->name, XNStatusDoneCallback)==0) {
00344       ic->core.status_attr.done_callback.client_data =
00345        ((XIMCallback *)p->value)->client_data;
00346       ic->core.status_attr.done_callback.callback =
00347        ((XIMCallback *)p->value)->callback;
00348       ic->ximp_icpart->value_mask |= XIMP_STS_CALLBAK;
00349 
00350     } else if (strcmp(p->name, XNStatusDrawCallback)==0) {
00351       ic->core.status_attr.draw_callback.client_data =
00352        ((XIMCallback *)p->value)->client_data;
00353       ic->core.status_attr.draw_callback.callback =
00354        ((XIMCallback *)p->value)->callback;
00355       ic->ximp_icpart->value_mask |= XIMP_STS_CALLBAK;
00356     }
00357   }
00358   return True;
00359 }
00360 
00361 char*
00362 SetICValueData(XicCommon ic, XIMArg *values, XICSetMode mode,
00363               XimpChangeaMask change_mask) {
00364   XIMArg *p;
00365   char *return_name = NULL;
00366 
00367   for (p = values; p->name != NULL; p++) {
00368     TRACE_MESSAGE('v', ("iiimp_SetICValueData: %s\n", p->name));
00369     if (strcmp(p->name, XNInputStyle) == 0) {
00370       if (mode == CREATE_IC) {
00371        /* already set */
00372        continue;
00373       } else if (mode == SET_IC) {
00374        return_name = p->name;
00375        break; /* Can't change this value */
00376       }
00377     } else if (strcmp(p->name, XNClientWindow)==0) {
00378       /* 4378199: Linux Htt: can not operate after WMDoc client is
00379                                           closed on VineLinux2.0
00380 
00381         Need to check client_window is valid or not before creating
00382         status, preedit and lookup
00383       */
00384       if(!IMCheckIMWindow(ic, (Window)p->value)) {
00385         return p->name;
00386       }
00387       if (!(ic->ximp_icpart->value_mask & XIMP_CLIENT_WIN)) {
00388        ic->core.client_window = (Window)p->value;
00389        ic->ximp_icpart->value_mask |= XIMP_CLIENT_WIN;
00390        if (!(XIMP_CHK_FOCUSWINMASK(ic))) {
00391          ic->core.focus_window = ic->core.client_window;
00392          XIMP_SET_FOCUSWINMASK2(ic, change_mask);
00393        }
00394        XIC_GUI(ic, change_status)((XIC)ic, STATUS_CREATE, NULL);
00395        XIC_GUI(ic, change_preedit)((XIC)ic, PREEDIT_CREATE, NULL);
00396        XIC_GUI(ic, change_lookup)((XIC)ic, LOOKUP_CREATE, NULL);
00397 
00398        SetScreenNumber(ic);
00399        FilterConfigureNotify(ic->core.im->core.display,
00400                            ic->core.focus_window,
00401                            NULL, (XPointer)ic);
00402       } else {
00403 #ifdef NO_CLIENTWIN_CHANGE
00404        return_name = p->name;
00405        break; /* Can't change this value */
00406 #else
00407        /* allow to change client window */
00408        /* destroy status/preedit/lookup */
00409        XIC_GUI(ic, change_preedit)((XIC)ic, PREEDIT_DESTROY, NULL);
00410        XIC_GUI(ic, change_status)((XIC)ic, STATUS_DESTROY, NULL);
00411        XIC_GUI(ic, change_lookup)((XIC)ic, LOOKUP_DESTROY, NULL);
00412 
00413        ic->core.client_window = (Window)p->value;
00414        if (!(XIMP_CHK_FOCUSWINMASK(ic))) {
00415          ic->core.focus_window = ic->core.client_window;
00416          XIMP_SET_FOCUSWINMASK2(ic, change_mask);
00417        }
00418 
00419        /* re-create status/preedit/lookup */
00420        XIC_GUI(ic, change_status)((XIC)ic, STATUS_CREATE, NULL);
00421        XIC_GUI(ic, change_preedit)((XIC)ic, PREEDIT_CREATE, NULL);
00422        XIC_GUI(ic, change_lookup)((XIC)ic, LOOKUP_CREATE, NULL);
00423 
00424        SetScreenNumber(ic);
00425        FilterConfigureNotify(ic->core.im->core.display,
00426                            ic->core.focus_window,
00427                            NULL, (XPointer)ic);
00428 #endif
00429       }
00430            
00431     } else if (strcmp(p->name, XNFocusWindow)==0) {
00432       Window old_focus_window = 0;
00433       if ((Window)p->value != 0 &&
00434          (Window)p->value == ic->core.focus_window) {
00435        continue;
00436       }
00437 #if 0
00438       ic->ximp_icpart->back_focus_win = ic->core.focus_window;
00439 #endif
00440 #ifdef linux
00441       /* 4378199: Linux Htt: can not operate after WMDoc client is
00442                                           closed on VineLinux2.0
00443 
00444         Need to check focus_window is valid or not before creating
00445         status, preedit and lookup
00446       */
00447       if(!IMCheckIMWindow(ic, (Window)p->value)) {
00448         return NULL;
00449       }
00450 #endif
00451 
00452       old_focus_window = ic->core.focus_window;
00453       ic->core.focus_window = (Window)p->value;
00454       XIMP_SET_FOCUSWINMASK2(ic, change_mask);
00455       XIC_GUI(ic, change_preedit)((XIC)ic, PREEDIT_CREATE, NULL);
00456 
00457       SetScreenNumber(ic);
00458       FilterConfigureNotify(ic->core.im->core.display,
00459                          ic->core.focus_window,
00460                          NULL, (XPointer)ic);
00461       if (XIM_IS_SWITCH(ic->core.im)) {
00462        SwitchKeyEventFilter(ic, old_focus_window);
00463       } else if (XIM_IS_IIIMP(ic->core.im)) {
00464        IIIMPKeyEventFilter(ic, old_focus_window);
00465       }
00466     } else if (strcmp(p->name, XNResourceName)==0) {
00467       ic->core.im->core.res_name = (char *)p->value;
00468       ic->ximp_icpart->value_mask |= XIMP_RES_NAME;
00469            
00470     } else if (strcmp(p->name, XNResourceClass)==0) {
00471       ic->core.im->core.res_class = (char *)p->value;
00472       ic->ximp_icpart->value_mask |= XIMP_RES_CLASS;
00473            
00474     } else if (strcmp(p->name, XNGeometryCallback)==0) {
00475       ic->core.geometry_callback.client_data =
00476        ((XIMCallback *)p->value)->client_data;
00477       ic->core.geometry_callback.callback =
00478        ((XIMCallback *)p->value)->callback;
00479       ic->ximp_icpart->value_mask |= XIMP_GEOMETRY_CB;
00480            
00481     } else if (strcmp(p->name, XNUnicodeCharacterSubset)==0) {
00482       /* select a input charset from the list */
00483       XIMUnicodeCharacterSubset *new_subset =
00484        (XIMUnicodeCharacterSubset*)p->value;
00485       if (!SelectCharacterSubset(ic, new_subset)) {
00486        break;               /* cannot set this value */
00487       }
00488     } else if (strcmp(p->name, XNPreeditAttributes)==0) {
00489       if (PreeditSetAttributes(ic,
00490                             &(ic->ximp_icpart->preedit_attr),
00491                             (XIMArg*)p->value, mode, change_mask,
00492                             return_name) == False )
00493        break;
00494            
00495     } else if (strcmp(p->name, XNStatusAttributes)==0) {
00496       if (StatusSetAttributes(ic,
00497                            &(ic->ximp_icpart->status_attr),
00498                            (XIMArg*)p->value, mode, change_mask,
00499                            return_name) == False )
00500        break;
00501 
00502       SwitchUpdateStatus(ic);
00503 
00504     } else if (strcmp(p->name, XNPreeditState)==0) {
00505       ic->core.preedit_attr.preedit_state = (XIMPreeditState)p->value;
00506       ChangePreeditState(ic);
00507     } else if (strcmp(p->name, XNPreeditStateNotifyCallback)==0) {
00508       ic->core.preedit_attr.state_notify_callback.client_data =
00509        ((XIMCallback *)p->value)->client_data;
00510       ic->core.preedit_attr.state_notify_callback.callback =
00511        ((XIMCallback *)p->value)->callback;
00512 
00513  /* private XIC extention */
00514     } else if (strcmp(p->name, XNLookupStartCallback)==0) {
00515       ic->lookup_start_callback.client_data =
00516        ((XIMCallback *)p->value)->client_data;
00517       ic->lookup_start_callback.callback =
00518        ((XIMCallback *)p->value)->callback;
00519     } else if (strcmp(p->name, XNLookupDrawCallback)==0) {
00520       ic->lookup_draw_callback.client_data =
00521        ((XIMCallback *)p->value)->client_data;
00522       ic->lookup_draw_callback.callback =
00523        ((XIMCallback *)p->value)->callback;
00524     } else if (strcmp(p->name, XNLookupDoneCallback)==0) {
00525       ic->lookup_done_callback.client_data =
00526        ((XIMCallback *)p->value)->client_data;
00527       ic->lookup_done_callback.callback =
00528        ((XIMCallback *)p->value)->callback;
00529 
00530     } else if (strcmp(p->name, XNSwitchIMNotifyCallback)==0) {
00531       ic->switchim_notify_callback.client_data =
00532        ((XIMCallback *)p->value)->client_data;
00533       ic->switchim_notify_callback.callback =
00534        ((XIMCallback *)p->value)->callback;
00535     } else if (strcmp(p->name, XNCommitStringCallback)==0) {
00536       ic->commit_string_callback.client_data =
00537        ((XIMCallback *)p->value)->client_data;
00538       ic->commit_string_callback.callback =
00539        ((XIMCallback *)p->value)->callback;
00540     } else if (strcmp(p->name, XNForwardEventCallback)==0) {
00541       ic->forward_event_callback.client_data =
00542        ((XIMCallback *)p->value)->client_data;
00543       ic->forward_event_callback.callback =
00544        ((XIMCallback *)p->value)->callback;
00545     } else {
00546       return_name = p->name;
00547       break;
00548     }
00549   }
00550   return return_name;
00551 }