8005096: Move a few source files in swing/beaninfo and in a demo.
Reviewed-by: ohair, erikj, malenkov
--- a/jdk/make/javax/swing/beaninfo/SwingBeans.gmk Tue Jan 08 13:15:54 2013 -0800
+++ b/jdk/make/javax/swing/beaninfo/SwingBeans.gmk Wed Jan 09 13:33:52 2013 +0100
@@ -124,10 +124,10 @@
$(BEANSRCDIR)/%BeanInfo.java: $(FAKESRC)/$(SWINGPKG)/%.java
@$(ECHO) $< >> $(TEMPDIR)/.beans.list
-$(BEANSRCDIR)/SwingBeanInfoBase.java: $(DOCLETSRC)/beaninfo/SwingBeanInfoBase.java
+$(BEANSRCDIR)/SwingBeanInfoBase.java: $(DOCLETSRC)/javax/swing/SwingBeanInfoBase.java
$(CP) $< $@
-$(BEANSRCDIR)/BeanInfoUtils.java: $(DOCLETSRC)/beaninfo/BeanInfoUtils.java
+$(BEANSRCDIR)/BeanInfoUtils.java: $(DOCLETSRC)/sun/swing/BeanInfoUtils.java
$(CP) $< $@
#
--- a/jdk/make/tools/swing-beans/beaninfo/BeanInfoUtils.java Tue Jan 08 13:15:54 2013 -0800
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,293 +0,0 @@
-/*
- * Copyright (c) 1998, 2004, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation. Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package sun.swing;
-
-import java.beans.*;
-import java.lang.reflect.Method;
-
-public class BeanInfoUtils
-{
- /* The values of these createPropertyDescriptor() and
- * createBeanDescriptor() keywords are the names of the
- * properties they're used to set.
- */
- public static final String BOUND = "bound";
- public static final String CONSTRAINED = "constrained";
- public static final String PROPERTYEDITORCLASS = "propertyEditorClass";
- public static final String READMETHOD = "readMethod";
- public static final String WRITEMETHOD = "writeMethod";
- public static final String DISPLAYNAME = "displayName";
- public static final String EXPERT = "expert";
- public static final String HIDDEN = "hidden";
- public static final String PREFERRED = "preferred";
- public static final String SHORTDESCRIPTION = "shortDescription";
- public static final String CUSTOMIZERCLASS = "customizerClass";
-
- static private void initFeatureDescriptor(FeatureDescriptor fd, String key, Object value)
- {
- if (DISPLAYNAME.equals(key)) {
- fd.setDisplayName((String)value);
- }
-
- if (EXPERT.equals(key)) {
- fd.setExpert(((Boolean)value).booleanValue());
- }
-
- if (HIDDEN.equals(key)) {
- fd.setHidden(((Boolean)value).booleanValue());
- }
-
- if (PREFERRED.equals(key)) {
- fd.setPreferred(((Boolean)value).booleanValue());
- }
-
- else if (SHORTDESCRIPTION.equals(key)) {
- fd.setShortDescription((String)value);
- }
-
- /* Otherwise assume that we have an arbitrary FeatureDescriptor
- * "attribute".
- */
- else {
- fd.setValue(key, value);
- }
- }
-
- /**
- * Create a beans PropertyDescriptor given an of keyword/value
- * arguments. The following sample call shows all of the supported
- * keywords:
- *<pre>
- * createPropertyDescriptor("contentPane", new Object[] {
- * BOUND, Boolean.TRUE,
- * CONSTRAINED, Boolean.TRUE,
- * PROPERTYEDITORCLASS, package.MyEditor.class,
- * READMETHOD, "getContentPane",
- * WRITEMETHOD, "setContentPane",
- * DISPLAYNAME, "contentPane",
- * EXPERT, Boolean.FALSE,
- * HIDDEN, Boolean.FALSE,
- * PREFERRED, Boolean.TRUE,
- * SHORTDESCRIPTION, "A top level window with a window manager border",
- * "random attribute","random object value"
- * }
- * );
- * </pre>
- * The keywords correspond to <code>java.beans.PropertyDescriptor</code> and
- * <code>java.beans.FeatureDescriptor</code> properties, e.g. providing a value
- * for displayName is comparable to <code>FeatureDescriptor.setDisplayName()</code>.
- * Using createPropertyDescriptor instead of the PropertyDescriptor
- * constructor and set methods is preferrable in that it regularizes
- * the code in a <code>java.beans.BeanInfo.getPropertyDescriptors()</code>
- * method implementation. One can use <code>createPropertyDescriptor</code>
- * to set <code>FeatureDescriptor</code> attributes, as in "random attribute"
- * "random object value".
- * <p>
- * All properties should provide a reasonable value for the
- * <code>SHORTDESCRIPTION</code> keyword and should set <code>BOUND</code>
- * to <code>Boolean.TRUE</code> if neccessary. The remaining keywords
- * are optional. There's no need to provide values for keywords like
- * READMETHOD if the correct value can be computed, i.e. if the properties
- * get/is method follows the standard beans pattern.
- * <p>
- * The PREFERRED keyword is not supported by the JDK1.1 java.beans package.
- * It's still worth setting it to true for properties that are most
- * likely to be interested to the average developer, e.g. AbstractButton.title
- * is a preferred property, AbstractButton.focusPainted is not.
- *
- * @see java.beans#BeanInfo
- * @see java.beans#PropertyDescriptor
- * @see java.beans#FeatureDescriptor
- */
- public static PropertyDescriptor createPropertyDescriptor(Class cls, String name, Object[] args)
- {
- PropertyDescriptor pd = null;
- try {
- pd = new PropertyDescriptor(name, cls);
- } catch (IntrospectionException e) {
- // Try creating a read-only property, in case setter isn't defined.
- try {
- pd = createReadOnlyPropertyDescriptor(name, cls);
- } catch (IntrospectionException ie) {
- throwError(ie, "Can't create PropertyDescriptor for " + name + " ");
- }
- }
-
- for(int i = 0; i < args.length; i += 2) {
- String key = (String)args[i];
- Object value = args[i + 1];
-
- if (BOUND.equals(key)) {
- pd.setBound(((Boolean)value).booleanValue());
- }
-
- else if (CONSTRAINED.equals(key)) {
- pd.setConstrained(((Boolean)value).booleanValue());
- }
-
- else if (PROPERTYEDITORCLASS.equals(key)) {
- pd.setPropertyEditorClass((Class)value);
- }
-
- else if (READMETHOD.equals(key)) {
- String methodName = (String)value;
- Method method;
- try {
- method = cls.getMethod(methodName, new Class[0]);
- pd.setReadMethod(method);
- }
- catch(Exception e) {
- throwError(e, cls + " no such method as \"" + methodName + "\"");
- }
- }
-
- else if (WRITEMETHOD.equals(key)) {
- String methodName = (String)value;
- Method method;
- try {
- Class type = pd.getPropertyType();
- method = cls.getMethod(methodName, new Class[]{type});
- pd.setWriteMethod(method);
- }
- catch(Exception e) {
- throwError(e, cls + " no such method as \"" + methodName + "\"");
- }
- }
-
- else {
- initFeatureDescriptor(pd, key, value);
- }
- }
-
- return pd;
- }
-
-
- /**
- * Create a BeanDescriptor object given an of keyword/value
- * arguments. The following sample call shows all of the supported
- * keywords:
- *<pre>
- * createBeanDescriptor(JWindow..class, new Object[] {
- * CUSTOMIZERCLASS, package.MyCustomizer.class,
- * DISPLAYNAME, "JFrame",
- * EXPERT, Boolean.FALSE,
- * HIDDEN, Boolean.FALSE,
- * PREFERRED, Boolean.TRUE,
- * SHORTDESCRIPTION, "A top level window with a window manager border",
- * "random attribute","random object value"
- * }
- * );
- * </pre>
- * The keywords correspond to <code>java.beans.BeanDescriptor</code> and
- * <code>java.beans.FeatureDescriptor</code> properties, e.g. providing a value
- * for displayName is comparable to <code>FeatureDescriptor.setDisplayName()</code>.
- * Using createBeanDescriptor instead of the BeanDescriptor
- * constructor and set methods is preferrable in that it regularizes
- * the code in a <code>java.beans.BeanInfo.getBeanDescriptor()</code>
- * method implementation. One can use <code>createBeanDescriptor</code>
- * to set <code>FeatureDescriptor</code> attributes, as in "random attribute"
- * "random object value".
- *
- * @see java.beans#BeanInfo
- * @see java.beans#PropertyDescriptor
- */
- public static BeanDescriptor createBeanDescriptor(Class cls, Object[] args)
- {
- Class customizerClass = null;
-
- /* For reasons I don't understand, customizerClass is a
- * readOnly property. So we have to find it and pass it
- * to the constructor here.
- */
- for(int i = 0; i < args.length; i += 2) {
- if (CUSTOMIZERCLASS.equals((String)args[i])) {
- customizerClass = (Class)args[i + 1];
- break;
- }
- }
-
- BeanDescriptor bd = new BeanDescriptor(cls, customizerClass);
-
- for(int i = 0; i < args.length; i += 2) {
- String key = (String)args[i];
- Object value = args[i + 1];
- initFeatureDescriptor(bd, key, value);
- }
-
- return bd;
- }
-
- static private PropertyDescriptor createReadOnlyPropertyDescriptor(
- String name, Class cls) throws IntrospectionException {
-
- Method readMethod = null;
- String base = capitalize(name);
- Class[] parameters = new Class[0];
-
- // Is it a boolean?
- try {
- readMethod = cls.getMethod("is" + base, parameters);
- } catch (Exception ex) {}
- if (readMethod == null) {
- try {
- // Try normal accessor pattern.
- readMethod = cls.getMethod("get" + base, parameters);
- } catch (Exception ex2) {}
- }
- if (readMethod != null) {
- return new PropertyDescriptor(name, readMethod, null);
- }
-
- try {
- // Try indexed accessor pattern.
- parameters = new Class[1];
- parameters[0] = int.class;
- readMethod = cls.getMethod("get" + base, parameters);
- } catch (NoSuchMethodException nsme) {
- throw new IntrospectionException(
- "cannot find accessor method for " + name + " property.");
- }
- return new IndexedPropertyDescriptor(name, null, null, readMethod, null);
- }
-
- // Modified methods from java.beans.Introspector
- private static String capitalize(String s) {
- if (s.length() == 0) {
- return s;
- }
- char chars[] = s.toCharArray();
- chars[0] = Character.toUpperCase(chars[0]);
- return new String(chars);
- }
-
- /**
- * Fatal errors are handled by calling this method.
- */
- public static void throwError(Exception e, String s) {
- throw new Error(e.toString() + " " + s);
- }
-}
--- a/jdk/make/tools/swing-beans/beaninfo/SwingBeanInfoBase.java Tue Jan 08 13:15:54 2013 -0800
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,82 +0,0 @@
-/*
- * Copyright (c) 1997, 2004, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation. Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package javax.swing;
-
-import java.beans.*;
-import java.lang.reflect.*;
-import java.awt.Image;
-
-/**
- * The superclass for all Swing BeanInfo classes. It provides
- * default implementations of <code>getIcon</code> and
- * <code>getDefaultPropertyIndex</code> as well as utility
- * methods, like createPropertyDescriptor, for writing BeanInfo
- * implementations. This classes is intended to be used along
- * with <code>GenSwingBeanInfo</code> a BeanInfo class code generator.
- *
- * @see GenSwingBeanInfo
- * @author Hans Muller
- */
-public class SwingBeanInfoBase extends SimpleBeanInfo
-{
- /**
- * The default index is always 0. In other words the first property
- * listed in the getPropertyDescriptors() method is the one
- * to show a (JFC builder) user in a situation where just a single
- * property will be shown.
- */
- public int getDefaultPropertyIndex() {
- return 0;
- }
-
- /**
- * Returns a generic Swing icon, all icon "kinds" are supported.
- * Subclasses should defer to this method when they don't have
- * a particular beans icon kind.
- */
- public Image getIcon(int kind) {
- // PENDING(hmuller) need generic swing icon images.
- return null;
- }
-
- /**
- * Returns the BeanInfo for the superclass of our bean, so that
- * its PropertyDescriptors will be included.
- */
- public BeanInfo[] getAdditionalBeanInfo() {
- Class superClass = getBeanDescriptor().getBeanClass().getSuperclass();
- BeanInfo superBeanInfo = null;
- try {
- superBeanInfo = Introspector.getBeanInfo(superClass);
- } catch (IntrospectionException ie) {}
- if (superBeanInfo != null) {
- BeanInfo[] ret = new BeanInfo[1];
- ret[0] = superBeanInfo;
- return ret;
- }
- return null;
- }
-}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/make/tools/swing-beans/javax/swing/SwingBeanInfoBase.java Wed Jan 09 13:33:52 2013 +0100
@@ -0,0 +1,82 @@
+/*
+ * Copyright (c) 1997, 2004, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation. Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package javax.swing;
+
+import java.beans.*;
+import java.lang.reflect.*;
+import java.awt.Image;
+
+/**
+ * The superclass for all Swing BeanInfo classes. It provides
+ * default implementations of <code>getIcon</code> and
+ * <code>getDefaultPropertyIndex</code> as well as utility
+ * methods, like createPropertyDescriptor, for writing BeanInfo
+ * implementations. This classes is intended to be used along
+ * with <code>GenSwingBeanInfo</code> a BeanInfo class code generator.
+ *
+ * @see GenSwingBeanInfo
+ * @author Hans Muller
+ */
+public class SwingBeanInfoBase extends SimpleBeanInfo
+{
+ /**
+ * The default index is always 0. In other words the first property
+ * listed in the getPropertyDescriptors() method is the one
+ * to show a (JFC builder) user in a situation where just a single
+ * property will be shown.
+ */
+ public int getDefaultPropertyIndex() {
+ return 0;
+ }
+
+ /**
+ * Returns a generic Swing icon, all icon "kinds" are supported.
+ * Subclasses should defer to this method when they don't have
+ * a particular beans icon kind.
+ */
+ public Image getIcon(int kind) {
+ // PENDING(hmuller) need generic swing icon images.
+ return null;
+ }
+
+ /**
+ * Returns the BeanInfo for the superclass of our bean, so that
+ * its PropertyDescriptors will be included.
+ */
+ public BeanInfo[] getAdditionalBeanInfo() {
+ Class superClass = getBeanDescriptor().getBeanClass().getSuperclass();
+ BeanInfo superBeanInfo = null;
+ try {
+ superBeanInfo = Introspector.getBeanInfo(superClass);
+ } catch (IntrospectionException ie) {}
+ if (superBeanInfo != null) {
+ BeanInfo[] ret = new BeanInfo[1];
+ ret[0] = superBeanInfo;
+ return ret;
+ }
+ return null;
+ }
+}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/make/tools/swing-beans/sun/swing/BeanInfoUtils.java Wed Jan 09 13:33:52 2013 +0100
@@ -0,0 +1,293 @@
+/*
+ * Copyright (c) 1998, 2004, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation. Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package sun.swing;
+
+import java.beans.*;
+import java.lang.reflect.Method;
+
+public class BeanInfoUtils
+{
+ /* The values of these createPropertyDescriptor() and
+ * createBeanDescriptor() keywords are the names of the
+ * properties they're used to set.
+ */
+ public static final String BOUND = "bound";
+ public static final String CONSTRAINED = "constrained";
+ public static final String PROPERTYEDITORCLASS = "propertyEditorClass";
+ public static final String READMETHOD = "readMethod";
+ public static final String WRITEMETHOD = "writeMethod";
+ public static final String DISPLAYNAME = "displayName";
+ public static final String EXPERT = "expert";
+ public static final String HIDDEN = "hidden";
+ public static final String PREFERRED = "preferred";
+ public static final String SHORTDESCRIPTION = "shortDescription";
+ public static final String CUSTOMIZERCLASS = "customizerClass";
+
+ static private void initFeatureDescriptor(FeatureDescriptor fd, String key, Object value)
+ {
+ if (DISPLAYNAME.equals(key)) {
+ fd.setDisplayName((String)value);
+ }
+
+ if (EXPERT.equals(key)) {
+ fd.setExpert(((Boolean)value).booleanValue());
+ }
+
+ if (HIDDEN.equals(key)) {
+ fd.setHidden(((Boolean)value).booleanValue());
+ }
+
+ if (PREFERRED.equals(key)) {
+ fd.setPreferred(((Boolean)value).booleanValue());
+ }
+
+ else if (SHORTDESCRIPTION.equals(key)) {
+ fd.setShortDescription((String)value);
+ }
+
+ /* Otherwise assume that we have an arbitrary FeatureDescriptor
+ * "attribute".
+ */
+ else {
+ fd.setValue(key, value);
+ }
+ }
+
+ /**
+ * Create a beans PropertyDescriptor given an of keyword/value
+ * arguments. The following sample call shows all of the supported
+ * keywords:
+ *<pre>
+ * createPropertyDescriptor("contentPane", new Object[] {
+ * BOUND, Boolean.TRUE,
+ * CONSTRAINED, Boolean.TRUE,
+ * PROPERTYEDITORCLASS, package.MyEditor.class,
+ * READMETHOD, "getContentPane",
+ * WRITEMETHOD, "setContentPane",
+ * DISPLAYNAME, "contentPane",
+ * EXPERT, Boolean.FALSE,
+ * HIDDEN, Boolean.FALSE,
+ * PREFERRED, Boolean.TRUE,
+ * SHORTDESCRIPTION, "A top level window with a window manager border",
+ * "random attribute","random object value"
+ * }
+ * );
+ * </pre>
+ * The keywords correspond to <code>java.beans.PropertyDescriptor</code> and
+ * <code>java.beans.FeatureDescriptor</code> properties, e.g. providing a value
+ * for displayName is comparable to <code>FeatureDescriptor.setDisplayName()</code>.
+ * Using createPropertyDescriptor instead of the PropertyDescriptor
+ * constructor and set methods is preferrable in that it regularizes
+ * the code in a <code>java.beans.BeanInfo.getPropertyDescriptors()</code>
+ * method implementation. One can use <code>createPropertyDescriptor</code>
+ * to set <code>FeatureDescriptor</code> attributes, as in "random attribute"
+ * "random object value".
+ * <p>
+ * All properties should provide a reasonable value for the
+ * <code>SHORTDESCRIPTION</code> keyword and should set <code>BOUND</code>
+ * to <code>Boolean.TRUE</code> if neccessary. The remaining keywords
+ * are optional. There's no need to provide values for keywords like
+ * READMETHOD if the correct value can be computed, i.e. if the properties
+ * get/is method follows the standard beans pattern.
+ * <p>
+ * The PREFERRED keyword is not supported by the JDK1.1 java.beans package.
+ * It's still worth setting it to true for properties that are most
+ * likely to be interested to the average developer, e.g. AbstractButton.title
+ * is a preferred property, AbstractButton.focusPainted is not.
+ *
+ * @see java.beans#BeanInfo
+ * @see java.beans#PropertyDescriptor
+ * @see java.beans#FeatureDescriptor
+ */
+ public static PropertyDescriptor createPropertyDescriptor(Class cls, String name, Object[] args)
+ {
+ PropertyDescriptor pd = null;
+ try {
+ pd = new PropertyDescriptor(name, cls);
+ } catch (IntrospectionException e) {
+ // Try creating a read-only property, in case setter isn't defined.
+ try {
+ pd = createReadOnlyPropertyDescriptor(name, cls);
+ } catch (IntrospectionException ie) {
+ throwError(ie, "Can't create PropertyDescriptor for " + name + " ");
+ }
+ }
+
+ for(int i = 0; i < args.length; i += 2) {
+ String key = (String)args[i];
+ Object value = args[i + 1];
+
+ if (BOUND.equals(key)) {
+ pd.setBound(((Boolean)value).booleanValue());
+ }
+
+ else if (CONSTRAINED.equals(key)) {
+ pd.setConstrained(((Boolean)value).booleanValue());
+ }
+
+ else if (PROPERTYEDITORCLASS.equals(key)) {
+ pd.setPropertyEditorClass((Class)value);
+ }
+
+ else if (READMETHOD.equals(key)) {
+ String methodName = (String)value;
+ Method method;
+ try {
+ method = cls.getMethod(methodName, new Class[0]);
+ pd.setReadMethod(method);
+ }
+ catch(Exception e) {
+ throwError(e, cls + " no such method as \"" + methodName + "\"");
+ }
+ }
+
+ else if (WRITEMETHOD.equals(key)) {
+ String methodName = (String)value;
+ Method method;
+ try {
+ Class type = pd.getPropertyType();
+ method = cls.getMethod(methodName, new Class[]{type});
+ pd.setWriteMethod(method);
+ }
+ catch(Exception e) {
+ throwError(e, cls + " no such method as \"" + methodName + "\"");
+ }
+ }
+
+ else {
+ initFeatureDescriptor(pd, key, value);
+ }
+ }
+
+ return pd;
+ }
+
+
+ /**
+ * Create a BeanDescriptor object given an of keyword/value
+ * arguments. The following sample call shows all of the supported
+ * keywords:
+ *<pre>
+ * createBeanDescriptor(JWindow..class, new Object[] {
+ * CUSTOMIZERCLASS, package.MyCustomizer.class,
+ * DISPLAYNAME, "JFrame",
+ * EXPERT, Boolean.FALSE,
+ * HIDDEN, Boolean.FALSE,
+ * PREFERRED, Boolean.TRUE,
+ * SHORTDESCRIPTION, "A top level window with a window manager border",
+ * "random attribute","random object value"
+ * }
+ * );
+ * </pre>
+ * The keywords correspond to <code>java.beans.BeanDescriptor</code> and
+ * <code>java.beans.FeatureDescriptor</code> properties, e.g. providing a value
+ * for displayName is comparable to <code>FeatureDescriptor.setDisplayName()</code>.
+ * Using createBeanDescriptor instead of the BeanDescriptor
+ * constructor and set methods is preferrable in that it regularizes
+ * the code in a <code>java.beans.BeanInfo.getBeanDescriptor()</code>
+ * method implementation. One can use <code>createBeanDescriptor</code>
+ * to set <code>FeatureDescriptor</code> attributes, as in "random attribute"
+ * "random object value".
+ *
+ * @see java.beans#BeanInfo
+ * @see java.beans#PropertyDescriptor
+ */
+ public static BeanDescriptor createBeanDescriptor(Class cls, Object[] args)
+ {
+ Class customizerClass = null;
+
+ /* For reasons I don't understand, customizerClass is a
+ * readOnly property. So we have to find it and pass it
+ * to the constructor here.
+ */
+ for(int i = 0; i < args.length; i += 2) {
+ if (CUSTOMIZERCLASS.equals((String)args[i])) {
+ customizerClass = (Class)args[i + 1];
+ break;
+ }
+ }
+
+ BeanDescriptor bd = new BeanDescriptor(cls, customizerClass);
+
+ for(int i = 0; i < args.length; i += 2) {
+ String key = (String)args[i];
+ Object value = args[i + 1];
+ initFeatureDescriptor(bd, key, value);
+ }
+
+ return bd;
+ }
+
+ static private PropertyDescriptor createReadOnlyPropertyDescriptor(
+ String name, Class cls) throws IntrospectionException {
+
+ Method readMethod = null;
+ String base = capitalize(name);
+ Class[] parameters = new Class[0];
+
+ // Is it a boolean?
+ try {
+ readMethod = cls.getMethod("is" + base, parameters);
+ } catch (Exception ex) {}
+ if (readMethod == null) {
+ try {
+ // Try normal accessor pattern.
+ readMethod = cls.getMethod("get" + base, parameters);
+ } catch (Exception ex2) {}
+ }
+ if (readMethod != null) {
+ return new PropertyDescriptor(name, readMethod, null);
+ }
+
+ try {
+ // Try indexed accessor pattern.
+ parameters = new Class[1];
+ parameters[0] = int.class;
+ readMethod = cls.getMethod("get" + base, parameters);
+ } catch (NoSuchMethodException nsme) {
+ throw new IntrospectionException(
+ "cannot find accessor method for " + name + " property.");
+ }
+ return new IndexedPropertyDescriptor(name, null, null, readMethod, null);
+ }
+
+ // Modified methods from java.beans.Introspector
+ private static String capitalize(String s) {
+ if (s.length() == 0) {
+ return s;
+ }
+ char chars[] = s.toCharArray();
+ chars[0] = Character.toUpperCase(chars[0]);
+ return new String(chars);
+ }
+
+ /**
+ * Fatal errors are handled by calling this method.
+ */
+ public static void throwError(Exception e, String s) {
+ throw new Error(e.toString() + " " + s);
+ }
+}
--- a/jdk/makefiles/CompileJavaClasses.gmk Tue Jan 08 13:15:54 2013 -0800
+++ b/jdk/makefiles/CompileJavaClasses.gmk Wed Jan 09 13:33:52 2013 +0100
@@ -292,6 +292,7 @@
$(JDK_TOPDIR)/src/$(OPENJDK_TARGET_OS_API_DIR)/classes \
$(MACOSX_SRC_DIRS) \
$(JDK_OUTPUTDIR)/gensrc \
+ $(JDK_OUTPUTDIR)/gensrc_no_srczip \
$(CLOSED_SRC_DIRS),\
INCLUDES:=$(JDK_USER_DEFINED_FILTER),\
EXCLUDES:=$(EXCLUDES),\
--- a/jdk/makefiles/GensrcSwing.gmk Tue Jan 08 13:15:54 2013 -0800
+++ b/jdk/makefiles/GensrcSwing.gmk Wed Jan 09 13:33:52 2013 +0100
@@ -45,7 +45,6 @@
# Generate beaninfo java files
#
-BEAN_GENSRC_DIR = $(JDK_OUTPUTDIR)/gensrc/javax/swing/beaninfo
DOCLETSRC_DIR = $(JDK_TOPDIR)/make/tools/swing-beans
# javax.swing package
@@ -69,25 +68,31 @@
# Dummy variable so far, in the old build system it was false by default
SWINGBEAN_DEBUG_FLAG = false
# GenDocletBeanInfo is compiled in Tools.gmk and picks up from $(JDK_OUTPUTDIR)/btclasses
-$(JDK_OUTPUTDIR)/gensrc/_the.generated_beaninfo: $(BEANS_SRC) $(BEAN_GENSRC_DIR)/SwingBeanInfoBase.java $(BEAN_GENSRC_DIR)/BeanInfoUtils.java $(BUILD_TOOLS)
+$(JDK_OUTPUTDIR)/gensrc_no_srczip/_the.generated_beaninfo: $(BEANS_SRC) $(JDK_OUTPUTDIR)/gensrc/javax/swing/SwingBeanInfoBase.java $(JDK_OUTPUTDIR)/gensrc/sun/swing/BeanInfoUtils.java $(BUILD_TOOLS)
$(ECHO) Generating beaninfo
- $(JAVA) -Djava.awt.headless=true -jar $(JAVADOC_JARS) -doclet GenDocletBeanInfo -x $(SWINGBEAN_DEBUG_FLAG) -d $(BEAN_GENSRC_DIR) -t $(DOCLETSRC_DIR)/SwingBeanInfo.template -docletpath $(JDK_OUTPUTDIR)/btclasses \
+ $(MKDIR) -p $(JDK_OUTPUTDIR)/gensrc_no_srczip/javax/swing
+ $(JAVA) -Djava.awt.headless=true -jar $(JAVADOC_JARS) -doclet GenDocletBeanInfo \
+ -x $(SWINGBEAN_DEBUG_FLAG) -d $(JDK_OUTPUTDIR)/gensrc_no_srczip/javax/swing \
+ -t $(DOCLETSRC_DIR)/SwingBeanInfo.template -docletpath $(JDK_OUTPUTDIR)/btclasses \
-XDignore.symbol.file=true \
-classpath $(JDK_OUTPUTDIR)/btclasses $(BEANS_SRC) $(LOG_INFO)
+# Move the JTextComponent into its proper package directory.
+ $(MKDIR) -p $(JDK_OUTPUTDIR)/gensrc_no_srczip/javax/swing/text
+ $(MV) $(JDK_OUTPUTDIR)/gensrc_no_srczip/javax/swing/JTextComponentBeanInfo.java $(JDK_OUTPUTDIR)/gensrc_no_srczip/javax/swing/text/JTextComponentBeanInfo.java
$(TOUCH) $@
# This file is the part of dt.jar
-# For some reason it is under $(JDK_TOPDIR)/make/tools/swing-beans/beaninfo
+# For some reason it is under $(JDK_TOPDIR)/make/tools/swing-beans/javax/swing
# Should it be moved under $(JDK_TOPDIR)/src/share/classes/javax/swing instead?
-$(BEAN_GENSRC_DIR)/SwingBeanInfoBase.java: $(DOCLETSRC_DIR)/beaninfo/SwingBeanInfoBase.java
+$(JDK_OUTPUTDIR)/gensrc/javax/swing/SwingBeanInfoBase.java: $(DOCLETSRC_DIR)/javax/swing/SwingBeanInfoBase.java
$(MKDIR) -p $(@D)
$(CP) $< $@
# This file is the part of dt.jar
-# For some reason it is under $(JDK_TOPDIR)/make/tools/swing-beans/beaninfo
+# For some reason it is under $(JDK_TOPDIR)/make/tools/swing-beans/sun/swing
# Should it be moved under $(JDK_TOPDIR)/src/share/classes/sun/swing instead?
-$(BEAN_GENSRC_DIR)/BeanInfoUtils.java: $(DOCLETSRC_DIR)/beaninfo/BeanInfoUtils.java
+$(JDK_OUTPUTDIR)/gensrc/sun/swing/BeanInfoUtils.java: $(DOCLETSRC_DIR)/sun/swing/BeanInfoUtils.java
$(MKDIR) -p $(@D)
$(CP) $< $@
-GENSRC_SWING_BEANINFO = $(JDK_OUTPUTDIR)/gensrc/_the.generated_beaninfo
+GENSRC_SWING_BEANINFO = $(JDK_OUTPUTDIR)/gensrc_no_srczip/_the.generated_beaninfo
--- a/jdk/src/share/demo/jfc/CodePointIM/CodePointInputMethod.java Tue Jan 08 13:15:54 2013 -0800
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,499 +0,0 @@
-/*
- * Copyright (c) 2002, 2011, Oracle and/or its affiliates. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * - Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * - Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * - Neither the name of Oracle nor the names of its
- * contributors may be used to endorse or promote products derived
- * from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
- * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
- * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
- * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
- * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
- * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
- * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-/*
- * This source code is provided to illustrate the usage of a given feature
- * or technique and has been deliberately simplified. Additional steps
- * required for a production-quality application, such as security checks,
- * input validation and proper error handling, might not be present in
- * this sample code.
- */
-
-package com.sun.inputmethods.internal.codepointim;
-
-
-import java.awt.AWTEvent;
-import java.awt.Toolkit;
-import java.awt.Rectangle;
-import java.awt.event.InputMethodEvent;
-import java.awt.event.KeyEvent;
-import java.awt.font.TextAttribute;
-import java.awt.font.TextHitInfo;
-import java.awt.im.InputMethodHighlight;
-import java.awt.im.spi.InputMethod;
-import java.awt.im.spi.InputMethodContext;
-import java.io.IOException;
-import java.text.AttributedString;
-import java.util.Locale;
-
-
-/**
- * The Code Point Input Method is a simple input method that allows Unicode
- * characters to be entered using their code point or code unit values. See the
- * accompanying file README.txt for more information.
- *
- * @author Brian Beck
- */
-public class CodePointInputMethod implements InputMethod {
-
- private static final int UNSET = 0;
- private static final int ESCAPE = 1; // \u0000 - \uFFFF
- private static final int SPECIAL_ESCAPE = 2; // \U000000 - \U10FFFF
- private static final int SURROGATE_PAIR = 3; // \uD800\uDC00 - \uDBFF\uDFFF
- private InputMethodContext context;
- private Locale locale;
- private StringBuffer buffer;
- private int insertionPoint;
- private int format = UNSET;
-
- public CodePointInputMethod() throws IOException {
- }
-
- /**
- * This is the input method's main routine. The composed text is stored
- * in buffer.
- */
- public void dispatchEvent(AWTEvent event) {
- // This input method handles KeyEvent only.
- if (!(event instanceof KeyEvent)) {
- return;
- }
-
- KeyEvent e = (KeyEvent) event;
- int eventID = event.getID();
- boolean notInCompositionMode = buffer.length() == 0;
-
- if (eventID == KeyEvent.KEY_PRESSED) {
- // If we are not in composition mode, pass through
- if (notInCompositionMode) {
- return;
- }
-
- switch (e.getKeyCode()) {
- case KeyEvent.VK_LEFT:
- moveCaretLeft();
- break;
- case KeyEvent.VK_RIGHT:
- moveCaretRight();
- break;
- }
- } else if (eventID == KeyEvent.KEY_TYPED) {
- char c = e.getKeyChar();
-
- // If we are not in composition mode, wait a back slash
- if (notInCompositionMode) {
- // If the type character is not a back slash, pass through
- if (c != '\\') {
- return;
- }
-
- startComposition(); // Enter to composition mode
- } else {
- switch (c) {
- case ' ': // Exit from composition mode
- finishComposition();
- break;
- case '\u007f': // Delete
- deleteCharacter();
- break;
- case '\b': // BackSpace
- deletePreviousCharacter();
- break;
- case '\u001b': // Escape
- cancelComposition();
- break;
- case '\n': // Return
- case '\t': // Tab
- sendCommittedText();
- break;
- default:
- composeUnicodeEscape(c);
- break;
- }
- }
- } else { // KeyEvent.KEY_RELEASED
- // If we are not in composition mode, pass through
- if (notInCompositionMode) {
- return;
- }
- }
-
- e.consume();
- }
-
- private void composeUnicodeEscape(char c) {
- switch (buffer.length()) {
- case 1: // \\
- waitEscapeCharacter(c);
- break;
- case 2: // \\u or \\U
- case 3: // \\ux or \\Ux
- case 4: // \\uxx or \\Uxx
- waitDigit(c);
- break;
- case 5: // \\uxxx or \\Uxxx
- if (format == SPECIAL_ESCAPE) {
- waitDigit(c);
- } else {
- waitDigit2(c);
- }
- break;
- case 6: // \\uxxxx or \\Uxxxx
- if (format == SPECIAL_ESCAPE) {
- waitDigit(c);
- } else if (format == SURROGATE_PAIR) {
- waitBackSlashOrLowSurrogate(c);
- } else {
- beep();
- }
- break;
- case 7: // \\Uxxxxx
- // Only SPECIAL_ESCAPE format uses this state.
- // Since the second "\\u" of SURROGATE_PAIR format is inserted
- // automatically, users don't have to type these keys.
- waitDigit(c);
- break;
- case 8: // \\uxxxx\\u
- case 9: // \\uxxxx\\ux
- case 10: // \\uxxxx\\uxx
- case 11: // \\uxxxx\\uxxx
- if (format == SURROGATE_PAIR) {
- waitDigit(c);
- } else {
- beep();
- }
- break;
- default:
- beep();
- break;
- }
- }
-
- private void waitEscapeCharacter(char c) {
- if (c == 'u' || c == 'U') {
- buffer.append(c);
- insertionPoint++;
- sendComposedText();
- format = (c == 'u') ? ESCAPE : SPECIAL_ESCAPE;
- } else {
- if (c != '\\') {
- buffer.append(c);
- insertionPoint++;
- }
- sendCommittedText();
- }
- }
-
- private void waitDigit(char c) {
- if (Character.digit(c, 16) != -1) {
- buffer.insert(insertionPoint++, c);
- sendComposedText();
- } else {
- beep();
- }
- }
-
- private void waitDigit2(char c) {
- if (Character.digit(c, 16) != -1) {
- buffer.insert(insertionPoint++, c);
- char codePoint = (char) getCodePoint(buffer, 2, 5);
- if (Character.isHighSurrogate(codePoint)) {
- format = SURROGATE_PAIR;
- buffer.append("\\u");
- insertionPoint = 8;
- } else {
- format = ESCAPE;
- }
- sendComposedText();
- } else {
- beep();
- }
- }
-
- private void waitBackSlashOrLowSurrogate(char c) {
- if (insertionPoint == 6) {
- if (c == '\\') {
- buffer.append(c);
- buffer.append('u');
- insertionPoint = 8;
- sendComposedText();
- } else if (Character.digit(c, 16) != -1) {
- buffer.append("\\u");
- buffer.append(c);
- insertionPoint = 9;
- sendComposedText();
- } else {
- beep();
- }
- } else {
- beep();
- }
- }
-
- /**
- * Send the composed text to the client.
- */
- private void sendComposedText() {
- AttributedString as = new AttributedString(buffer.toString());
- as.addAttribute(TextAttribute.INPUT_METHOD_HIGHLIGHT,
- InputMethodHighlight.SELECTED_RAW_TEXT_HIGHLIGHT);
- context.dispatchInputMethodEvent(
- InputMethodEvent.INPUT_METHOD_TEXT_CHANGED,
- as.getIterator(), 0,
- TextHitInfo.leading(insertionPoint), null);
- }
-
- /**
- * Send the committed text to the client.
- */
- private void sendCommittedText() {
- AttributedString as = new AttributedString(buffer.toString());
- context.dispatchInputMethodEvent(
- InputMethodEvent.INPUT_METHOD_TEXT_CHANGED,
- as.getIterator(), buffer.length(),
- TextHitInfo.leading(insertionPoint), null);
-
- buffer.setLength(0);
- insertionPoint = 0;
- format = UNSET;
- }
-
- /**
- * Move the insertion point one position to the left in the composed text.
- * Do not let the caret move to the left of the "\\u" or "\\U".
- */
- private void moveCaretLeft() {
- int len = buffer.length();
- if (--insertionPoint < 2) {
- insertionPoint++;
- beep();
- } else if (format == SURROGATE_PAIR && insertionPoint == 7) {
- insertionPoint = 8;
- beep();
- }
-
- context.dispatchInputMethodEvent(
- InputMethodEvent.CARET_POSITION_CHANGED,
- null, 0,
- TextHitInfo.leading(insertionPoint), null);
- }
-
- /**
- * Move the insertion point one position to the right in the composed text.
- */
- private void moveCaretRight() {
- int len = buffer.length();
- if (++insertionPoint > len) {
- insertionPoint = len;
- beep();
- }
-
- context.dispatchInputMethodEvent(
- InputMethodEvent.CARET_POSITION_CHANGED,
- null, 0,
- TextHitInfo.leading(insertionPoint), null);
- }
-
- /**
- * Delete the character preceding the insertion point in the composed text.
- * If the insertion point is not at the end of the composed text and the
- * preceding text is "\\u" or "\\U", ring the bell.
- */
- private void deletePreviousCharacter() {
- if (insertionPoint == 2) {
- if (buffer.length() == 2) {
- cancelComposition();
- } else {
- // Do not allow deletion of the leading "\\u" or "\\U" if there
- // are other digits in the composed text.
- beep();
- }
- } else if (insertionPoint == 8) {
- if (buffer.length() == 8) {
- if (format == SURROGATE_PAIR) {
- buffer.deleteCharAt(--insertionPoint);
- }
- buffer.deleteCharAt(--insertionPoint);
- sendComposedText();
- } else {
- // Do not allow deletion of the second "\\u" if there are other
- // digits in the composed text.
- beep();
- }
- } else {
- buffer.deleteCharAt(--insertionPoint);
- if (buffer.length() == 0) {
- sendCommittedText();
- } else {
- sendComposedText();
- }
- }
- }
-
- /**
- * Delete the character following the insertion point in the composed text.
- * If the insertion point is at the end of the composed text, ring the bell.
- */
- private void deleteCharacter() {
- if (insertionPoint < buffer.length()) {
- buffer.deleteCharAt(insertionPoint);
- sendComposedText();
- } else {
- beep();
- }
- }
-
- private void startComposition() {
- buffer.append('\\');
- insertionPoint = 1;
- sendComposedText();
- }
-
- private void cancelComposition() {
- buffer.setLength(0);
- insertionPoint = 0;
- sendCommittedText();
- }
-
- private void finishComposition() {
- int len = buffer.length();
- if (len == 6 && format != SPECIAL_ESCAPE) {
- char codePoint = (char) getCodePoint(buffer, 2, 5);
- if (Character.isValidCodePoint(codePoint) && codePoint != 0xFFFF) {
- buffer.setLength(0);
- buffer.append(codePoint);
- sendCommittedText();
- return;
- }
- } else if (len == 8 && format == SPECIAL_ESCAPE) {
- int codePoint = getCodePoint(buffer, 2, 7);
- if (Character.isValidCodePoint(codePoint) && codePoint != 0xFFFF) {
- buffer.setLength(0);
- buffer.appendCodePoint(codePoint);
- sendCommittedText();
- return;
- }
- } else if (len == 12 && format == SURROGATE_PAIR) {
- char[] codePoint = {
- (char) getCodePoint(buffer, 2, 5),
- (char) getCodePoint(buffer, 8, 11)
- };
- if (Character.isHighSurrogate(codePoint[0]) && Character.
- isLowSurrogate(codePoint[1])) {
- buffer.setLength(0);
- buffer.append(codePoint);
- sendCommittedText();
- return;
- }
- }
-
- beep();
- }
-
- private int getCodePoint(StringBuffer sb, int from, int to) {
- int value = 0;
- for (int i = from; i <= to; i++) {
- value = (value << 4) + Character.digit(sb.charAt(i), 16);
- }
- return value;
- }
-
- private static void beep() {
- Toolkit.getDefaultToolkit().beep();
- }
-
- public void activate() {
- if (buffer == null) {
- buffer = new StringBuffer(12);
- insertionPoint = 0;
- }
- }
-
- public void deactivate(boolean isTemporary) {
- if (!isTemporary) {
- buffer = null;
- }
- }
-
- public void dispose() {
- }
-
- public Object getControlObject() {
- return null;
- }
-
- public void endComposition() {
- sendCommittedText();
- }
-
- public Locale getLocale() {
- return locale;
- }
-
- public void hideWindows() {
- }
-
- public boolean isCompositionEnabled() {
- // always enabled
- return true;
- }
-
- public void notifyClientWindowChange(Rectangle location) {
- }
-
- public void reconvert() {
- // not supported yet
- throw new UnsupportedOperationException();
- }
-
- public void removeNotify() {
- }
-
- public void setCharacterSubsets(Character.Subset[] subsets) {
- }
-
- public void setCompositionEnabled(boolean enable) {
- // not supported yet
- throw new UnsupportedOperationException();
- }
-
- public void setInputMethodContext(InputMethodContext context) {
- this.context = context;
- }
-
- /*
- * The Code Point Input Method supports all locales.
- */
- public boolean setLocale(Locale locale) {
- this.locale = locale;
- return true;
- }
-}
--- a/jdk/src/share/demo/jfc/CodePointIM/CodePointInputMethodDescriptor.java Tue Jan 08 13:15:54 2013 -0800
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,94 +0,0 @@
-/*
- * Copyright (c) 2002, 2011, Oracle and/or its affiliates. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * - Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * - Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * - Neither the name of Oracle nor the names of its
- * contributors may be used to endorse or promote products derived
- * from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
- * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
- * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
- * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
- * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
- * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
- * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-/*
- * This source code is provided to illustrate the usage of a given feature
- * or technique and has been deliberately simplified. Additional steps
- * required for a production-quality application, such as security checks,
- * input validation and proper error handling, might not be present in
- * this sample code.
- */
-
-package com.sun.inputmethods.internal.codepointim;
-
-
-import java.awt.Image;
-import java.awt.im.spi.InputMethodDescriptor;
-import java.awt.im.spi.InputMethod;
-import java.util.Locale;
-
-
-/**
- * The CodePointInputMethod is a simple input method that allows Unicode
- * characters to be entered via their hexadecimal code point values.
- *
- * The class, CodePointInputMethodDescriptor, provides information about the
- * CodePointInputMethod which allows it to be selected and loaded by the
- * Input Method Framework.
- */
-public class CodePointInputMethodDescriptor implements InputMethodDescriptor {
-
- public CodePointInputMethodDescriptor() {
- }
-
- /**
- * Creates a new instance of the Code Point input method.
- *
- * @return a new instance of the Code Point input method
- * @exception Exception any exception that may occur while creating the
- * input method instance
- */
- public InputMethod createInputMethod() throws Exception {
- return new CodePointInputMethod();
- }
-
- /**
- * This input method can be used by any locale.
- */
- public Locale[] getAvailableLocales() {
- Locale[] locales = {
- new Locale("", "", ""), };
- return locales;
- }
-
- public synchronized String getInputMethodDisplayName(Locale inputLocale,
- Locale displayLanguage) {
- return "CodePoint Input Method";
- }
-
- public Image getInputMethodIcon(Locale inputLocale) {
- return null;
- }
-
- public boolean hasDynamicLocaleList() {
- return false;
- }
-}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/share/demo/jfc/CodePointIM/com/sun/inputmethods/internal/codepointim/CodePointInputMethod.java Wed Jan 09 13:33:52 2013 +0100
@@ -0,0 +1,499 @@
+/*
+ * Copyright (c) 2002, 2011, Oracle and/or its affiliates. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *
+ * - Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * - Neither the name of Oracle nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
+ * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/*
+ * This source code is provided to illustrate the usage of a given feature
+ * or technique and has been deliberately simplified. Additional steps
+ * required for a production-quality application, such as security checks,
+ * input validation and proper error handling, might not be present in
+ * this sample code.
+ */
+
+package com.sun.inputmethods.internal.codepointim;
+
+
+import java.awt.AWTEvent;
+import java.awt.Toolkit;
+import java.awt.Rectangle;
+import java.awt.event.InputMethodEvent;
+import java.awt.event.KeyEvent;
+import java.awt.font.TextAttribute;
+import java.awt.font.TextHitInfo;
+import java.awt.im.InputMethodHighlight;
+import java.awt.im.spi.InputMethod;
+import java.awt.im.spi.InputMethodContext;
+import java.io.IOException;
+import java.text.AttributedString;
+import java.util.Locale;
+
+
+/**
+ * The Code Point Input Method is a simple input method that allows Unicode
+ * characters to be entered using their code point or code unit values. See the
+ * accompanying file README.txt for more information.
+ *
+ * @author Brian Beck
+ */
+public class CodePointInputMethod implements InputMethod {
+
+ private static final int UNSET = 0;
+ private static final int ESCAPE = 1; // \u0000 - \uFFFF
+ private static final int SPECIAL_ESCAPE = 2; // \U000000 - \U10FFFF
+ private static final int SURROGATE_PAIR = 3; // \uD800\uDC00 - \uDBFF\uDFFF
+ private InputMethodContext context;
+ private Locale locale;
+ private StringBuffer buffer;
+ private int insertionPoint;
+ private int format = UNSET;
+
+ public CodePointInputMethod() throws IOException {
+ }
+
+ /**
+ * This is the input method's main routine. The composed text is stored
+ * in buffer.
+ */
+ public void dispatchEvent(AWTEvent event) {
+ // This input method handles KeyEvent only.
+ if (!(event instanceof KeyEvent)) {
+ return;
+ }
+
+ KeyEvent e = (KeyEvent) event;
+ int eventID = event.getID();
+ boolean notInCompositionMode = buffer.length() == 0;
+
+ if (eventID == KeyEvent.KEY_PRESSED) {
+ // If we are not in composition mode, pass through
+ if (notInCompositionMode) {
+ return;
+ }
+
+ switch (e.getKeyCode()) {
+ case KeyEvent.VK_LEFT:
+ moveCaretLeft();
+ break;
+ case KeyEvent.VK_RIGHT:
+ moveCaretRight();
+ break;
+ }
+ } else if (eventID == KeyEvent.KEY_TYPED) {
+ char c = e.getKeyChar();
+
+ // If we are not in composition mode, wait a back slash
+ if (notInCompositionMode) {
+ // If the type character is not a back slash, pass through
+ if (c != '\\') {
+ return;
+ }
+
+ startComposition(); // Enter to composition mode
+ } else {
+ switch (c) {
+ case ' ': // Exit from composition mode
+ finishComposition();
+ break;
+ case '\u007f': // Delete
+ deleteCharacter();
+ break;
+ case '\b': // BackSpace
+ deletePreviousCharacter();
+ break;
+ case '\u001b': // Escape
+ cancelComposition();
+ break;
+ case '\n': // Return
+ case '\t': // Tab
+ sendCommittedText();
+ break;
+ default:
+ composeUnicodeEscape(c);
+ break;
+ }
+ }
+ } else { // KeyEvent.KEY_RELEASED
+ // If we are not in composition mode, pass through
+ if (notInCompositionMode) {
+ return;
+ }
+ }
+
+ e.consume();
+ }
+
+ private void composeUnicodeEscape(char c) {
+ switch (buffer.length()) {
+ case 1: // \\
+ waitEscapeCharacter(c);
+ break;
+ case 2: // \\u or \\U
+ case 3: // \\ux or \\Ux
+ case 4: // \\uxx or \\Uxx
+ waitDigit(c);
+ break;
+ case 5: // \\uxxx or \\Uxxx
+ if (format == SPECIAL_ESCAPE) {
+ waitDigit(c);
+ } else {
+ waitDigit2(c);
+ }
+ break;
+ case 6: // \\uxxxx or \\Uxxxx
+ if (format == SPECIAL_ESCAPE) {
+ waitDigit(c);
+ } else if (format == SURROGATE_PAIR) {
+ waitBackSlashOrLowSurrogate(c);
+ } else {
+ beep();
+ }
+ break;
+ case 7: // \\Uxxxxx
+ // Only SPECIAL_ESCAPE format uses this state.
+ // Since the second "\\u" of SURROGATE_PAIR format is inserted
+ // automatically, users don't have to type these keys.
+ waitDigit(c);
+ break;
+ case 8: // \\uxxxx\\u
+ case 9: // \\uxxxx\\ux
+ case 10: // \\uxxxx\\uxx
+ case 11: // \\uxxxx\\uxxx
+ if (format == SURROGATE_PAIR) {
+ waitDigit(c);
+ } else {
+ beep();
+ }
+ break;
+ default:
+ beep();
+ break;
+ }
+ }
+
+ private void waitEscapeCharacter(char c) {
+ if (c == 'u' || c == 'U') {
+ buffer.append(c);
+ insertionPoint++;
+ sendComposedText();
+ format = (c == 'u') ? ESCAPE : SPECIAL_ESCAPE;
+ } else {
+ if (c != '\\') {
+ buffer.append(c);
+ insertionPoint++;
+ }
+ sendCommittedText();
+ }
+ }
+
+ private void waitDigit(char c) {
+ if (Character.digit(c, 16) != -1) {
+ buffer.insert(insertionPoint++, c);
+ sendComposedText();
+ } else {
+ beep();
+ }
+ }
+
+ private void waitDigit2(char c) {
+ if (Character.digit(c, 16) != -1) {
+ buffer.insert(insertionPoint++, c);
+ char codePoint = (char) getCodePoint(buffer, 2, 5);
+ if (Character.isHighSurrogate(codePoint)) {
+ format = SURROGATE_PAIR;
+ buffer.append("\\u");
+ insertionPoint = 8;
+ } else {
+ format = ESCAPE;
+ }
+ sendComposedText();
+ } else {
+ beep();
+ }
+ }
+
+ private void waitBackSlashOrLowSurrogate(char c) {
+ if (insertionPoint == 6) {
+ if (c == '\\') {
+ buffer.append(c);
+ buffer.append('u');
+ insertionPoint = 8;
+ sendComposedText();
+ } else if (Character.digit(c, 16) != -1) {
+ buffer.append("\\u");
+ buffer.append(c);
+ insertionPoint = 9;
+ sendComposedText();
+ } else {
+ beep();
+ }
+ } else {
+ beep();
+ }
+ }
+
+ /**
+ * Send the composed text to the client.
+ */
+ private void sendComposedText() {
+ AttributedString as = new AttributedString(buffer.toString());
+ as.addAttribute(TextAttribute.INPUT_METHOD_HIGHLIGHT,
+ InputMethodHighlight.SELECTED_RAW_TEXT_HIGHLIGHT);
+ context.dispatchInputMethodEvent(
+ InputMethodEvent.INPUT_METHOD_TEXT_CHANGED,
+ as.getIterator(), 0,
+ TextHitInfo.leading(insertionPoint), null);
+ }
+
+ /**
+ * Send the committed text to the client.
+ */
+ private void sendCommittedText() {
+ AttributedString as = new AttributedString(buffer.toString());
+ context.dispatchInputMethodEvent(
+ InputMethodEvent.INPUT_METHOD_TEXT_CHANGED,
+ as.getIterator(), buffer.length(),
+ TextHitInfo.leading(insertionPoint), null);
+
+ buffer.setLength(0);
+ insertionPoint = 0;
+ format = UNSET;
+ }
+
+ /**
+ * Move the insertion point one position to the left in the composed text.
+ * Do not let the caret move to the left of the "\\u" or "\\U".
+ */
+ private void moveCaretLeft() {
+ int len = buffer.length();
+ if (--insertionPoint < 2) {
+ insertionPoint++;
+ beep();
+ } else if (format == SURROGATE_PAIR && insertionPoint == 7) {
+ insertionPoint = 8;
+ beep();
+ }
+
+ context.dispatchInputMethodEvent(
+ InputMethodEvent.CARET_POSITION_CHANGED,
+ null, 0,
+ TextHitInfo.leading(insertionPoint), null);
+ }
+
+ /**
+ * Move the insertion point one position to the right in the composed text.
+ */
+ private void moveCaretRight() {
+ int len = buffer.length();
+ if (++insertionPoint > len) {
+ insertionPoint = len;
+ beep();
+ }
+
+ context.dispatchInputMethodEvent(
+ InputMethodEvent.CARET_POSITION_CHANGED,
+ null, 0,
+ TextHitInfo.leading(insertionPoint), null);
+ }
+
+ /**
+ * Delete the character preceding the insertion point in the composed text.
+ * If the insertion point is not at the end of the composed text and the
+ * preceding text is "\\u" or "\\U", ring the bell.
+ */
+ private void deletePreviousCharacter() {
+ if (insertionPoint == 2) {
+ if (buffer.length() == 2) {
+ cancelComposition();
+ } else {
+ // Do not allow deletion of the leading "\\u" or "\\U" if there
+ // are other digits in the composed text.
+ beep();
+ }
+ } else if (insertionPoint == 8) {
+ if (buffer.length() == 8) {
+ if (format == SURROGATE_PAIR) {
+ buffer.deleteCharAt(--insertionPoint);
+ }
+ buffer.deleteCharAt(--insertionPoint);
+ sendComposedText();
+ } else {
+ // Do not allow deletion of the second "\\u" if there are other
+ // digits in the composed text.
+ beep();
+ }
+ } else {
+ buffer.deleteCharAt(--insertionPoint);
+ if (buffer.length() == 0) {
+ sendCommittedText();
+ } else {
+ sendComposedText();
+ }
+ }
+ }
+
+ /**
+ * Delete the character following the insertion point in the composed text.
+ * If the insertion point is at the end of the composed text, ring the bell.
+ */
+ private void deleteCharacter() {
+ if (insertionPoint < buffer.length()) {
+ buffer.deleteCharAt(insertionPoint);
+ sendComposedText();
+ } else {
+ beep();
+ }
+ }
+
+ private void startComposition() {
+ buffer.append('\\');
+ insertionPoint = 1;
+ sendComposedText();
+ }
+
+ private void cancelComposition() {
+ buffer.setLength(0);
+ insertionPoint = 0;
+ sendCommittedText();
+ }
+
+ private void finishComposition() {
+ int len = buffer.length();
+ if (len == 6 && format != SPECIAL_ESCAPE) {
+ char codePoint = (char) getCodePoint(buffer, 2, 5);
+ if (Character.isValidCodePoint(codePoint) && codePoint != 0xFFFF) {
+ buffer.setLength(0);
+ buffer.append(codePoint);
+ sendCommittedText();
+ return;
+ }
+ } else if (len == 8 && format == SPECIAL_ESCAPE) {
+ int codePoint = getCodePoint(buffer, 2, 7);
+ if (Character.isValidCodePoint(codePoint) && codePoint != 0xFFFF) {
+ buffer.setLength(0);
+ buffer.appendCodePoint(codePoint);
+ sendCommittedText();
+ return;
+ }
+ } else if (len == 12 && format == SURROGATE_PAIR) {
+ char[] codePoint = {
+ (char) getCodePoint(buffer, 2, 5),
+ (char) getCodePoint(buffer, 8, 11)
+ };
+ if (Character.isHighSurrogate(codePoint[0]) && Character.
+ isLowSurrogate(codePoint[1])) {
+ buffer.setLength(0);
+ buffer.append(codePoint);
+ sendCommittedText();
+ return;
+ }
+ }
+
+ beep();
+ }
+
+ private int getCodePoint(StringBuffer sb, int from, int to) {
+ int value = 0;
+ for (int i = from; i <= to; i++) {
+ value = (value << 4) + Character.digit(sb.charAt(i), 16);
+ }
+ return value;
+ }
+
+ private static void beep() {
+ Toolkit.getDefaultToolkit().beep();
+ }
+
+ public void activate() {
+ if (buffer == null) {
+ buffer = new StringBuffer(12);
+ insertionPoint = 0;
+ }
+ }
+
+ public void deactivate(boolean isTemporary) {
+ if (!isTemporary) {
+ buffer = null;
+ }
+ }
+
+ public void dispose() {
+ }
+
+ public Object getControlObject() {
+ return null;
+ }
+
+ public void endComposition() {
+ sendCommittedText();
+ }
+
+ public Locale getLocale() {
+ return locale;
+ }
+
+ public void hideWindows() {
+ }
+
+ public boolean isCompositionEnabled() {
+ // always enabled
+ return true;
+ }
+
+ public void notifyClientWindowChange(Rectangle location) {
+ }
+
+ public void reconvert() {
+ // not supported yet
+ throw new UnsupportedOperationException();
+ }
+
+ public void removeNotify() {
+ }
+
+ public void setCharacterSubsets(Character.Subset[] subsets) {
+ }
+
+ public void setCompositionEnabled(boolean enable) {
+ // not supported yet
+ throw new UnsupportedOperationException();
+ }
+
+ public void setInputMethodContext(InputMethodContext context) {
+ this.context = context;
+ }
+
+ /*
+ * The Code Point Input Method supports all locales.
+ */
+ public boolean setLocale(Locale locale) {
+ this.locale = locale;
+ return true;
+ }
+}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/share/demo/jfc/CodePointIM/com/sun/inputmethods/internal/codepointim/CodePointInputMethodDescriptor.java Wed Jan 09 13:33:52 2013 +0100
@@ -0,0 +1,94 @@
+/*
+ * Copyright (c) 2002, 2011, Oracle and/or its affiliates. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *
+ * - Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * - Neither the name of Oracle nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
+ * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/*
+ * This source code is provided to illustrate the usage of a given feature
+ * or technique and has been deliberately simplified. Additional steps
+ * required for a production-quality application, such as security checks,
+ * input validation and proper error handling, might not be present in
+ * this sample code.
+ */
+
+package com.sun.inputmethods.internal.codepointim;
+
+
+import java.awt.Image;
+import java.awt.im.spi.InputMethodDescriptor;
+import java.awt.im.spi.InputMethod;
+import java.util.Locale;
+
+
+/**
+ * The CodePointInputMethod is a simple input method that allows Unicode
+ * characters to be entered via their hexadecimal code point values.
+ *
+ * The class, CodePointInputMethodDescriptor, provides information about the
+ * CodePointInputMethod which allows it to be selected and loaded by the
+ * Input Method Framework.
+ */
+public class CodePointInputMethodDescriptor implements InputMethodDescriptor {
+
+ public CodePointInputMethodDescriptor() {
+ }
+
+ /**
+ * Creates a new instance of the Code Point input method.
+ *
+ * @return a new instance of the Code Point input method
+ * @exception Exception any exception that may occur while creating the
+ * input method instance
+ */
+ public InputMethod createInputMethod() throws Exception {
+ return new CodePointInputMethod();
+ }
+
+ /**
+ * This input method can be used by any locale.
+ */
+ public Locale[] getAvailableLocales() {
+ Locale[] locales = {
+ new Locale("", "", ""), };
+ return locales;
+ }
+
+ public synchronized String getInputMethodDisplayName(Locale inputLocale,
+ Locale displayLanguage) {
+ return "CodePoint Input Method";
+ }
+
+ public Image getInputMethodIcon(Locale inputLocale) {
+ return null;
+ }
+
+ public boolean hasDynamicLocaleList() {
+ return false;
+ }
+}