--- old/src/java.desktop/unix/native/libawt_xawt/awt/awt_InputMethod.c 2018-06-15 17:37:35.260196355 +0900 +++ new/src/java.desktop/unix/native/libawt_xawt/awt/awt_InputMethod.c 2018-06-15 17:37:34.617209462 +0900 @@ -175,6 +175,9 @@ static void setX11InputMethodData(JNIEnv *, jobject, X11InputMethodData *); static void destroyX11InputMethodData(JNIEnv *, X11InputMethodData *); static void freeX11InputMethodData(JNIEnv *, X11InputMethodData *); +#if defined(__linux__) || defined(MACOSX) +static Window getParentWindow(Window); +#endif #ifdef __solaris__ /* Prototype for this function is missing in Solaris X11R6 Xlib.h */ @@ -1018,9 +1021,28 @@ } } + // The code set the IC mode that the preedit state is not initialied + // at XmbResetIC. This attribute can be set at XCreateIC. I separately + // set the attribute to avoid the failure of XCreateIC at some platform + // which does not support the attribute. + if (pX11IMData->ic_active != 0) + XSetICValues(pX11IMData->ic_active, + XNResetState, XIMInitialState, + NULL); + if (pX11IMData->ic_passive != 0 + && pX11IMData->ic_active != pX11IMData->ic_passive) + XSetICValues(pX11IMData->ic_passive, + XNResetState, XIMInitialState, + NULL); + /* Add the global reference object to X11InputMethod to the list. */ addToX11InputMethodGRefList(pX11IMData->x11inputmethod); + /* Unset focus to avoid unexpected IM on */ + setXICFocus(pX11IMData->ic_active, False); + if (pX11IMData->ic_active != pX11IMData->ic_passive) + setXICFocus(pX11IMData->ic_passive, False); + return True; err: @@ -1161,6 +1183,29 @@ { /*ARGSUSED*/ /*printf("StatusDoneCallback:\n"); */ + JNIEnv *env = GetJNIEnv(); + X11InputMethodData *pX11IMData = NULL; + StatusWindow *statusWindow; + + AWT_LOCK(); + + if (!isX11InputMethodGRefInList((jobject)client_data)) { + if ((jobject)client_data == currentX11InputMethodInstance) { + currentX11InputMethodInstance = NULL; + } + goto finally; + } + + if (NULL == (pX11IMData = getX11InputMethodData(env, (jobject)client_data)) + || NULL == (statusWindow = pX11IMData->statusWindow)){ + goto finally; + } + currentX11InputMethodInstance = (jobject)client_data; + + onoffStatusWindow(pX11IMData, 0, False); + + finally: + AWT_UNLOCK(); } static void @@ -1545,6 +1590,10 @@ { X11InputMethodData *pX11IMData; char * ret = NULL; + XVaNestedList pr_atrb; +#if defined(__linux__) || defined(MACOSX) + Boolean calledXSetICFocus = False; +#endif AWT_LOCK(); pX11IMData = getX11InputMethodData(env, this); @@ -1554,11 +1603,39 @@ return JNI_FALSE; } - ret = XSetICValues(pX11IMData->current_ic, XNPreeditState, - (enable ? XIMPreeditEnable : XIMPreeditDisable), NULL); +#if defined(__linux__) || defined(MACOSX) + if (NULL != pX11IMData->statusWindow) { + Window focus = 0; + int revert_to; + Window w = 0; + XGetInputFocus(awt_display, &focus, &revert_to); + XGetICValues(pX11IMData->current_ic, XNFocusWindow, &w, NULL); + if (RevertToPointerRoot == revert_to + && pX11IMData->ic_active != pX11IMData->ic_passive) { + if (pX11IMData->current_ic == pX11IMData->ic_active) { + if (getParentWindow(focus) == getParentWindow(w)) { + XUnsetICFocus(pX11IMData->ic_active); + calledXSetICFocus = True; + } + } + } + } +#endif + pr_atrb = XVaCreateNestedList(0, + XNPreeditState, (enable ? XIMPreeditEnable : XIMPreeditDisable), + NULL); + ret = XSetICValues(pX11IMData->current_ic, XNPreeditAttributes, pr_atrb, NULL); + XFree((void *)pr_atrb); +#if defined(__linux__) || defined(MACOSX) + if (calledXSetICFocus) { + XSetICFocus(pX11IMData->ic_active); + } +#endif AWT_UNLOCK(); - if ((ret != 0) && (strcmp(ret, XNPreeditState) == 0)) { + if ((ret != 0) + && ((strcmp(ret, XNPreeditAttributes) == 0) + || (strcmp(ret, XNPreeditState) == 0))) { JNU_ThrowByName(env, "java/lang/UnsupportedOperationException", ""); } @@ -1581,7 +1658,8 @@ { X11InputMethodData *pX11IMData = NULL; char * ret = NULL; - XIMPreeditState state; + XIMPreeditState state = XIMPreeditUnKnown; + XVaNestedList pr_atrb; AWT_LOCK(); pX11IMData = getX11InputMethodData(env, this); @@ -1591,10 +1669,14 @@ return JNI_FALSE; } - ret = XGetICValues(pX11IMData->current_ic, XNPreeditState, &state, NULL); + pr_atrb = XVaCreateNestedList(0, XNPreeditState, &state, NULL); + ret = XGetICValues(pX11IMData->current_ic, XNPreeditAttributes, pr_atrb, NULL); + XFree((void *)pr_atrb); AWT_UNLOCK(); - if ((ret != 0) && (strcmp(ret, XNPreeditState) == 0)) { + if ((ret != 0) + && ((strcmp(ret, XNPreeditAttributes) == 0) + || (strcmp(ret, XNPreeditState) == 0))) { JNU_ThrowByName(env, "java/lang/UnsupportedOperationException", ""); return JNI_FALSE; } @@ -1611,3 +1693,20 @@ AWT_UNLOCK(); #endif } + +#if defined(__linux__) || defined(MACOSX) +static Window getParentWindow(Window w) +{ + Window root=None, parent=None, *ignore_children=NULL; + unsigned int ignore_uint=0; + Status status = 0; + + if (w == None) + return None; + status = XQueryTree(dpy, w, &root, &parent, &ignore_children, &ignore_uint); + XFree(ignore_children); + if (status == 0) + return None; + return parent; +} +#endif