Display the XIM status callbacks with a popup window. (Patch from

Fri Dec  7 16:05:22 2001  Owen Taylor  <otaylor@redhat.com>

        * modules/input/gtkimcontextxim.c: Display the XIM
        status callbacks with a popup window. (Patch from
        HideToshi Tajima, #50628, somewhat modified.)
This commit is contained in:
Owen Taylor 2001-12-07 23:15:32 +00:00 committed by Owen Taylor
parent 880d279933
commit 9fd70c6bf5
9 changed files with 237 additions and 7 deletions

View File

@ -1,3 +1,9 @@
Fri Dec 7 16:05:22 2001 Owen Taylor <otaylor@redhat.com>
* modules/input/gtkimcontextxim.c: Display the XIM
status callbacks with a popup window. (Patch from
HideToshi Tajima, #50628, somewhat modified.)
Fri Dec 7 12:07:15 2001 Tim Janik <timj@gtk.org>
* gtk/Makefile.am: each source generation rule needs to use its own

View File

@ -1,3 +1,9 @@
Fri Dec 7 16:05:22 2001 Owen Taylor <otaylor@redhat.com>
* modules/input/gtkimcontextxim.c: Display the XIM
status callbacks with a popup window. (Patch from
HideToshi Tajima, #50628, somewhat modified.)
Fri Dec 7 12:07:15 2001 Tim Janik <timj@gtk.org>
* gtk/Makefile.am: each source generation rule needs to use its own

View File

@ -1,3 +1,9 @@
Fri Dec 7 16:05:22 2001 Owen Taylor <otaylor@redhat.com>
* modules/input/gtkimcontextxim.c: Display the XIM
status callbacks with a popup window. (Patch from
HideToshi Tajima, #50628, somewhat modified.)
Fri Dec 7 12:07:15 2001 Tim Janik <timj@gtk.org>
* gtk/Makefile.am: each source generation rule needs to use its own

View File

@ -1,3 +1,9 @@
Fri Dec 7 16:05:22 2001 Owen Taylor <otaylor@redhat.com>
* modules/input/gtkimcontextxim.c: Display the XIM
status callbacks with a popup window. (Patch from
HideToshi Tajima, #50628, somewhat modified.)
Fri Dec 7 12:07:15 2001 Tim Janik <timj@gtk.org>
* gtk/Makefile.am: each source generation rule needs to use its own

View File

@ -1,3 +1,9 @@
Fri Dec 7 16:05:22 2001 Owen Taylor <otaylor@redhat.com>
* modules/input/gtkimcontextxim.c: Display the XIM
status callbacks with a popup window. (Patch from
HideToshi Tajima, #50628, somewhat modified.)
Fri Dec 7 12:07:15 2001 Tim Janik <timj@gtk.org>
* gtk/Makefile.am: each source generation rule needs to use its own

View File

@ -1,3 +1,9 @@
Fri Dec 7 16:05:22 2001 Owen Taylor <otaylor@redhat.com>
* modules/input/gtkimcontextxim.c: Display the XIM
status callbacks with a popup window. (Patch from
HideToshi Tajima, #50628, somewhat modified.)
Fri Dec 7 12:07:15 2001 Tim Janik <timj@gtk.org>
* gtk/Makefile.am: each source generation rule needs to use its own

View File

@ -1,3 +1,9 @@
Fri Dec 7 16:05:22 2001 Owen Taylor <otaylor@redhat.com>
* modules/input/gtkimcontextxim.c: Display the XIM
status callbacks with a popup window. (Patch from
HideToshi Tajima, #50628, somewhat modified.)
Fri Dec 7 12:07:15 2001 Tim Janik <timj@gtk.org>
* gtk/Makefile.am: each source generation rule needs to use its own

View File

@ -20,7 +20,9 @@
#include "locale.h"
#include <string.h>
#include "gtk/gtklabel.h"
#include "gtk/gtksignal.h"
#include "gtk/gtkwindow.h"
#include "gtkimcontextxim.h"
struct _GtkXIMInfo
@ -49,6 +51,11 @@ static void gtk_im_context_xim_get_preedit_string (GtkIMContext *co
PangoAttrList **attrs,
gint *cursor_pos);
static void status_window_show (GtkIMContextXIM *context_xim);
static void status_window_hide (GtkIMContextXIM *context_xim);
static void status_window_set_text (GtkIMContextXIM *context_xim,
const gchar *text);
static XIC gtk_im_context_xim_get_ic (GtkIMContextXIM *context_xim);
static GObjectClass *parent_class;
@ -397,6 +404,9 @@ gtk_im_context_xim_focus_in (GtkIMContext *context)
return;
XSetICFocus (ic);
status_window_show (context_xim);
return;
}
@ -410,6 +420,9 @@ gtk_im_context_xim_focus_out (GtkIMContext *context)
return;
XUnsetICFocus (ic);
status_window_hide (context_xim);
return;
}
@ -473,6 +486,9 @@ gtk_im_context_xim_reset (GtkIMContext *context)
return;
if (context_xim->preedit_length == 0)
return;
preedit_attr = XVaCreateNestedList(0,
XNPreeditState, &preedit_state,
0);
@ -609,7 +625,6 @@ preedit_start_callback (XIC xic,
GtkIMContext *context = GTK_IM_CONTEXT (client_data);
g_signal_emit_by_name (context, "preedit_start");
g_print ("Starting preedit!\n");
}
static void
@ -620,7 +635,6 @@ preedit_done_callback (XIC xic,
GtkIMContext *context = GTK_IM_CONTEXT (client_data);
g_signal_emit_by_name (context, "preedit_end");
g_print ("Ending preedit!\n");
}
static gint
@ -773,7 +787,7 @@ status_start_callback (XIC xic,
XPointer client_data,
XPointer call_data)
{
g_print ("Status start\n");
return;
}
static void
@ -781,7 +795,7 @@ status_done_callback (XIC xic,
XPointer client_data,
XPointer call_data)
{
g_print ("Status done!\n");
return;
}
static void
@ -791,18 +805,19 @@ status_draw_callback (XIC xic,
{
GtkIMContextXIM *context = GTK_IM_CONTEXT_XIM (client_data);
g_print ("Status draw\n");
if (call_data->type == XIMTextType)
{
gchar *text;
xim_text_to_utf8 (context, call_data->data.text, &text);
if (text)
g_print (" %s\n", text);
status_window_set_text (context, text);
else
status_window_set_text (context, "");
}
else /* bitmap */
{
g_print (" bitmap id = %#lx\n", call_data->data.bitmap);
g_print ("Status drawn with bitmap - id = %#lx\n", call_data->data.bitmap);
}
}
@ -889,3 +904,175 @@ gtk_im_context_xim_get_ic (GtkIMContextXIM *context_xim)
return context_xim->ic;
}
/**************************
* *
* Status Window handling *
* *
**************************/
static gboolean
status_window_expose_event (GtkWidget *widget,
GdkEventExpose *event)
{
gdk_draw_rectangle (widget->window,
widget->style->base_gc [GTK_STATE_NORMAL],
TRUE,
0, 0,
widget->allocation.width, widget->allocation.height);
gdk_draw_rectangle (widget->window,
widget->style->text_gc [GTK_STATE_NORMAL],
FALSE,
0, 0,
widget->allocation.width - 1, widget->allocation.height - 1);
return FALSE;
}
static void
status_window_style_set (GtkWidget *toplevel,
GtkStyle *previous_style,
GtkWidget *label)
{
gint i;
for (i = 0; i < 5; i++)
gtk_widget_modify_fg (label, i, &toplevel->style->text[i]);
}
static void
status_window_destroy (GtkWidget *toplevel,
GtkWidget *status_window)
{
gtk_widget_destroy (status_window);
g_object_set_data (G_OBJECT (toplevel), "gtk-im-xim-status-window", NULL);
}
static gboolean
status_window_configure (GtkWidget *toplevel,
GdkEventConfigure *event,
GtkWidget *status_window)
{
GdkRectangle rect;
GtkRequisition requisition;
gint y;
gdk_window_get_frame_extents (toplevel->window, &rect);
gtk_widget_size_request (status_window, &requisition);
if (rect.y + rect.height + requisition.height < gdk_screen_height ())
y = rect.y + rect.height;
else
y = gdk_screen_height () - requisition.height;
gtk_window_move (GTK_WINDOW (status_window), rect.x, y);
return FALSE;
}
static GtkWidget *
status_window_get (GtkIMContextXIM *context_xim,
gboolean create)
{
GdkWindow *toplevel_gdk;
GtkWidget *toplevel;
GtkWidget *status_window;
GtkWidget *status_label;
if (!context_xim->client_window)
return NULL;
toplevel_gdk = context_xim->client_window;
while (TRUE)
{
GdkWindow *parent = gdk_window_get_parent (toplevel_gdk);
if (parent == gdk_get_default_root_window ())
break;
else
toplevel_gdk = parent;
}
gdk_window_get_user_data (toplevel_gdk, (gpointer *)&toplevel);
if (!toplevel)
return NULL;
status_window = g_object_get_data (G_OBJECT (toplevel), "gtk-im-xim-status-window");
if (status_window || !create)
return status_window;
status_window = gtk_window_new (GTK_WINDOW_POPUP);
gtk_window_set_policy (GTK_WINDOW (status_window), FALSE, FALSE, FALSE);
gtk_widget_set_app_paintable (status_window, TRUE);
status_label = gtk_label_new ("");
gtk_misc_set_padding (GTK_MISC (status_label), 1, 1);
gtk_widget_show (status_label);
gtk_container_add (GTK_CONTAINER (status_window), status_label);
g_signal_connect (toplevel, "destroy",
G_CALLBACK (status_window_destroy), status_window);
g_signal_connect (toplevel, "configure_event",
G_CALLBACK (status_window_configure), status_window);
status_window_configure (toplevel, NULL, status_window);
g_signal_connect (status_window, "style_set",
G_CALLBACK (status_window_style_set), status_label);
g_signal_connect (status_window, "expose_event",
G_CALLBACK (status_window_expose_event), NULL);
g_object_set_data (G_OBJECT (toplevel), "gtk-im-xim-status-window", status_window);
return status_window;
}
static gboolean
status_window_has_text (GtkWidget *status_window)
{
GtkWidget *label = GTK_BIN (status_window)->child;
const gchar *text = gtk_label_get_text (GTK_LABEL (label));
return text[0] != '\0';
}
static void
status_window_show (GtkIMContextXIM *context_xim)
{
GtkWidget *status_window = status_window_get (context_xim, TRUE);
context_xim->status_visible = TRUE;
if (status_window && status_window_has_text (status_window))
gtk_widget_show (status_window);
}
static void
status_window_hide (GtkIMContextXIM *context_xim)
{
GtkWidget *status_window = status_window_get (context_xim, FALSE);
context_xim->status_visible = FALSE;
if (status_window)
gtk_widget_hide (status_window);
}
static void
status_window_set_text (GtkIMContextXIM *context_xim,
const gchar *text)
{
GtkWidget *status_window = status_window_get (context_xim, TRUE);
if (status_window)
{
GtkWidget *label = GTK_BIN (status_window)->child;
gtk_label_set_text (GTK_LABEL (label), text);
if (context_xim->status_visible && status_window_has_text (status_window))
gtk_widget_show (status_window);
else
gtk_widget_hide (status_window);
}
}

View File

@ -72,6 +72,7 @@ struct _GtkIMContextXIM
XIC ic;
guint use_preedit : 1;
guint status_visible : 1;
};
struct _GtkIMContextXIMClass