]> Pileus Git - ~andy/gtk/blobdiff - gtk/gtkimcontextsimple.c
GtkLabelAccessible: Sanity check _get_text() input values
[~andy/gtk] / gtk / gtkimcontextsimple.c
index bd581f8c5357afdc6041472c1669cbd38bb9dc88..87debf226b9baaaeb4f3c3729aa6b25b79933e0b 100644 (file)
@@ -12,9 +12,7 @@
  * Lesser General Public License for more details.
  *
  * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the
- * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
- * Boston, MA 02111-1307, USA.
+ * License along with this library. If not, see <http://www.gnu.org/licenses/>.
  */
 
 #include "config.h"
@@ -270,7 +268,6 @@ check_table (GtkIMContextSimple    *context_simple,
          gunichar value = 
            0x10000 * seq[table->max_seq_len] + seq[table->max_seq_len + 1];
 
-         
          /* We found a tentative match. See if there are any longer
           * sequences containing this subsequence
           */
@@ -281,7 +278,7 @@ check_table (GtkIMContextSimple    *context_simple,
                {
                  priv->tentative_match = value;
                  priv->tentative_match_len = n_compose;
-               
+
                  g_signal_emit_by_name (context_simple, "preedit-changed");
 
                  return TRUE;
@@ -367,27 +364,91 @@ check_win32_special_case_after_compact_match (GtkIMContextSimple    *context_sim
 
 #endif
 
+#ifdef GDK_WINDOWING_QUARTZ
+
 static gboolean
-check_compact_table (GtkIMContextSimple    *context_simple,
-            const GtkComposeTableCompact *table,
-            gint                   n_compose)
+check_quartz_special_cases (GtkIMContextSimple *context_simple,
+                            gint                n_compose)
+{
+  GtkIMContextSimplePrivate *priv = context_simple->priv;
+  guint value = 0;
+
+  if (n_compose == 2)
+    {
+      switch (priv->compose_buffer[0])
+        {
+        case GDK_KEY_dead_doubleacute:
+          switch (priv->compose_buffer[1])
+            {
+            case GDK_KEY_dead_doubleacute:
+            case GDK_KEY_space:
+              value = GDK_KEY_quotedbl; break;
+
+            case 'a': value = GDK_KEY_adiaeresis; break;
+            case 'A': value = GDK_KEY_Adiaeresis; break;
+            case 'e': value = GDK_KEY_ediaeresis; break;
+            case 'E': value = GDK_KEY_Ediaeresis; break;
+            case 'i': value = GDK_KEY_idiaeresis; break;
+            case 'I': value = GDK_KEY_Idiaeresis; break;
+            case 'o': value = GDK_KEY_odiaeresis; break;
+            case 'O': value = GDK_KEY_Odiaeresis; break;
+            case 'u': value = GDK_KEY_udiaeresis; break;
+            case 'U': value = GDK_KEY_Udiaeresis; break;
+            case 'y': value = GDK_KEY_ydiaeresis; break;
+            case 'Y': value = GDK_KEY_Ydiaeresis; break;
+            }
+          break;
+
+        case GDK_KEY_dead_acute:
+          switch (priv->compose_buffer[1])
+            {
+            case 'c': value = GDK_KEY_ccedilla; break;
+            case 'C': value = GDK_KEY_Ccedilla; break;
+            }
+          break;
+        }
+    }
+
+  if (value > 0)
+    {
+      gtk_im_context_simple_commit_char (GTK_IM_CONTEXT (context_simple),
+                                         gdk_keyval_to_unicode (value));
+      priv->compose_buffer[0] = 0;
+
+      GTK_NOTE (MISC, g_print ("quartz: U+%04X\n", value));
+      return TRUE;
+    }
+
+  return FALSE;
+}
+
+#endif
+
+static gboolean
+check_compact_table (GtkIMContextSimple           *context_simple,
+                     const GtkComposeTableCompact *table,
+                     gint                          n_compose)
 {
   GtkIMContextSimplePrivate *priv = context_simple->priv;
   gint row_stride;
   guint16 *seq_index;
-  guint16 *seq; 
+  guint16 *seq;
   gint i;
+  gboolean match;
+  gunichar value;
 
   /* Will never match, if the sequence in the compose buffer is longer
    * than the sequences in the table.  Further, compare_seq (key, val)
-   * will overrun val if key is longer than val. */
+   * will overrun val if key is longer than val.
+   */
   if (n_compose > table->max_seq_len)
     return FALSE;
 
   seq_index = bsearch (priv->compose_buffer,
-                table->data, table->n_index_size,
-                sizeof (guint16) *  table->n_index_stride, 
-                compare_seq_index);
+                       table->data,
+                       table->n_index_size,
+                       sizeof (guint16) * table->n_index_stride,
+                       compare_seq_index);
 
   if (!seq_index)
     {
@@ -403,44 +464,47 @@ check_compact_table (GtkIMContextSimple    *context_simple,
 
   GTK_NOTE (MISC, g_print ("compact: %d ", *seq_index));
   seq = NULL;
+  match = FALSE;
 
-  for (i = n_compose-1; i < table->max_seq_len; i++)
+  for (i = n_compose - 1; i < table->max_seq_len; i++)
     {
       row_stride = i + 1;
 
-      if (seq_index[i+1] - seq_index[i] > 0)
+      if (seq_index[i + 1] - seq_index[i] > 0)
         {
-         seq = bsearch (priv->compose_buffer + 1,
-                table->data + seq_index[i], (seq_index[i+1] - seq_index[i]) / row_stride,
-                sizeof (guint16) *  row_stride, 
-                compare_seq);
+          seq = bsearch (priv->compose_buffer + 1,
+                         table->data + seq_index[i],
+                         (seq_index[i + 1] - seq_index[i]) / row_stride,
+                         sizeof (guint16) *  row_stride,
+                         compare_seq);
 
-         if (seq)
+          if (seq)
             {
               if (i == n_compose - 1)
-                break;
+                {
+                  value = seq[row_stride - 1];
+                  match = TRUE;
+                }
               else
                 {
+                  if (match)
+                    {
+                      GTK_NOTE (MISC, g_print ("tentative match U+%04X ", value));
+                      priv->tentative_match = value;
+                      priv->tentative_match_len = n_compose;
+                    }
+
                   g_signal_emit_by_name (context_simple, "preedit-changed");
 
-                 GTK_NOTE (MISC, g_print ("yes\n"));
-                 return TRUE;
+                  GTK_NOTE (MISC, g_print ("yes\n"));
+                  return TRUE;
                 }
              }
         }
     }
 
-  if (!seq)
-    {
-      GTK_NOTE (MISC, g_print ("no\n"));
-      return FALSE;
-    }
-  else
+  if (match)
     {
-      gunichar value;
-
-      value = seq[row_stride - 1];
-
       gtk_im_context_simple_commit_char (GTK_IM_CONTEXT (context_simple), value);
 #ifdef G_OS_WIN32
       check_win32_special_case_after_compact_match (context_simple, n_compose, value);
@@ -456,7 +520,7 @@ check_compact_table (GtkIMContextSimple    *context_simple,
 }
 
 /* This function receives a sequence of Unicode characters and tries to
- * normalize it (NFC). We check for the case the the resulting string
+ * normalize it (NFC). We check for the case where the resulting string
  * has length 1 (single character).
  * NFC normalisation normally rearranges diacritic marks, unless these
  * belong to the same Canonical Combining Class.
@@ -1064,6 +1128,11 @@ gtk_im_context_simple_filter_keypress (GtkIMContext *context,
        return TRUE;
 #endif
 
+#ifdef GDK_WINDOWING_QUARTZ
+      if (check_quartz_special_cases (context_simple, n_compose))
+        return TRUE;
+#endif
+
       if (check_compact_table (context_simple, &gtk_compose_table_compact, n_compose))
         return TRUE;