📄 beanstylesupport.java
字号:
// returns EventListener rather than PropertyStateListener because Beans // Binding (and thus PropertyStateListener) is optional -- by not having it // in the method signature, the classload and thus requirement can be // delayed until the method is actually called private synchronized EventListener getPropertyStateListener( PseudoclassListener listener, PseudoclassEvent event) { if (propertyStateListeners == null) propertyStateListeners = new HashMap<PseudoclassListener, EventListener>(); EventListener result = propertyStateListeners.get(listener); if (result == null) { result = new PseudoclassPropertyStateListener(listener, event); propertyStateListeners.put(listener, result); } return result; } private synchronized ELProperty getELProperty(String expression) { if (elProperties == null) elProperties = new HashMap<String, ELProperty>(); ELProperty result = elProperties.get(expression); if (result == null) { result = ELProperty.create(expression); elProperties.put(expression, result); } return result; } private String transformPseudoclass(String pseudoclass) { if (pseudoclass.equals("enabled")) pseudoclass = "${enabled}"; else if (pseudoclass.equals("disabled")) pseudoclass = "${!enabled}"; else if (pseudoclass.equals("selected")) pseudoclass = "${selected}"; else if (pseudoclass.equals("deselected")) pseudoclass = "${!selected}"; return pseudoclass; } /** * Adds a listener which will be notified as the specified pseudoclass is * added to or removed from this object. For example, {@link * java.awt.Component Components} support the <code>mouseover</code> * pseudoclass, and adding a <code>PseudoclassListener</code> with the * <code>mouseover</code> pseudoclass will cause it to receive notifications * as the mouse enters and exits the component. * *@param styleable object to which the listener is being added *@param pseudoclass the pseudoclass to listen for *@param listener the listener which will receive pseudoclass notifications *@throws StylesheetException if the specified pseudoclass is not supported by this * object *@see #removePseudoclassListener */ public void addPseudoclassListener(DefaultStyleable styleable, String pseudoclass, final PseudoclassListener listener) throws StylesheetException { final PseudoclassEvent event = new PseudoclassEvent(styleable, pseudoclass); Object object = styleable.getBaseObject(); pseudoclass = transformPseudoclass(pseudoclass); // add listeners if (pseudoclass.startsWith("{")) { ELProperty property = getELProperty("$" + pseudoclass); if (Boolean.TRUE.equals(property.getValue(object))) listener.pseudoclassAdded(event); property.addPropertyStateListener(object, (PropertyStateListener) getPropertyStateListener(listener, event)); } else throw new StylesheetException(beanClass + " does not support pseudoclass " + pseudoclass); } /** * Removes a pseudoclass listener from this object. * *@param styleable object from which the listener is being removed *@param pseudoclass the pseudoclass which was being listened for *@param listener the listener to remove *@throws StylesheetException if the specified pseudoclass is not supported by this * object *@see #addPseudoclassListener */ public void removePseudoclassListener(DefaultStyleable styleable, String pseudoclass, final PseudoclassListener listener) throws StylesheetException { Object object = styleable.getBaseObject(); pseudoclass = transformPseudoclass(pseudoclass); // remove listeners if (pseudoclass.startsWith("{")) { ELProperty property = getELProperty("$" + pseudoclass); property.removePropertyStateListener(object, (PropertyStateListener) getPropertyStateListener(listener, null)); } else throw new StylesheetException(beanClass + " does not support pseudoclass " + pseudoclass); } /** * Maps string values onto integers, so that int-valued enumeration * properties can be specified by strings. For example, when passed a key * of 'alignment', this method should normally map the values 'left', * 'center', and 'right' onto SwingConstants.LEFT, SwingConstants.CENTER, * and SwingConstants.RIGHT respectively. * <p> * You do not normally need to call this method yourself; it is invoked by * {@link #convertFromString} when an int-valued property has a value which * is not a valid number. By default, this method looks at the * <code>enumerationValues</code> value of the * <code>PropertyDescriptor</code>. * *@param key the name of the int-typed property *@param value the non-numeric value that was specified for the property *@throws IllegalArgumentException if the property is an enumeration, but * the value is not valid *@throws NumberFormatException if the property is not an enumeration */ protected int constantValue(String key, String value) { BeanInfo beanInfo = getBeanInfo(); PropertyDescriptor[] properties = beanInfo.getPropertyDescriptors(); String lowercaseValue = value.toLowerCase(); for (int i = 0; i < properties.length; i++) { if (properties[i].getName().equals(key)) { Object[] values = (Object[]) properties[i].getValue( "enumerationValues"); if (values != null) { for (int j = 0; j < values.length - 2; j += 3) { if (((String) values[j]).toLowerCase().equals( lowercaseValue)) return ((Integer) values[j + 1]).intValue(); } StringBuffer message = new StringBuffer("value of '" + key + "' must be one of: ["); for (int j = 0; j < values.length - 2; j += 3) { if (j != 0) message.append(", "); message.append(((String) values[j]).toLowerCase()); } message.append("] (found '" + value + "')"); throw new IllegalArgumentException(message.toString()); } } } throw new NumberFormatException(value); } /** * As {@link TypeManager#convertFromString(String, Class)}, except that it * additionally supports simple constant names for <code>int</code>-valued * types. * *@param key the name of the property whose value is being converted *@param value the raw string value of the property as it appears in the XML *@param type the datatype to convert the string into *@see #constantValue */ protected Object convertFromString(String key, String value, Class type) { try { return TypeManager.convertFromString(value, type); } catch (NumberFormatException e) { if (type == int.class || type == Integer.class) return new Integer(constantValue(key, value)); else throw e; } } /** * Returns the object's parent. The default implementation returns * <code>null</code>. */ public Styleable getStyleableParent(Object object) { return null; } /** * Returns the object's children. The default implementation returns * <code>null</code>. */ public Styleable[] getStyleableChildren(Object object) { return null; } /** * Returns the object's ID. The default implementation returns * <code>null</code>. */ public String getID(Object object) { return null; } /** * Returns an array of all Java classes which should be considered matches * for the object. The default implementation returns the base object class * plus all implemented interfaces. */ public Class[] getObjectClasses(Object object) { try { init(); } catch (IntrospectionException e) { throw new RuntimeException(e); } return classes; } /** * Returns the object's style class. The default implementation returns * <code>null</code>. */ public String getStyleClass(Object object) { return null; } /** * Returns a string representation of this object. */ public String toString() { return getClass().getName() + "[" + getBeanClass().getName() + "]"; }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -