Java/Reflection/JavaBean

Материал из Java эксперт
Перейти к: навигация, поиск

Get Color

   <source lang="java">

/* Java Reflection in Action Ira R. Forman and Nate Forman ISBN 1932394184 Publisher: Manning Publications Co.

  • /

import java.awt.Color; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; public class GetColor {

 static public void main(String[] args) {
   Rabbit rabbit = new Rabbit();
   //start extract snippet3
   setObjectColor(rabbit, Color.WHITE);
   //stop extract snippet3
   if (!rabbit.setColorCalled)
     throw new RuntimeException();
 }
 //start extract setObjectColor
 public static void setObjectColor(Object obj, Color color) {
   Class cls = obj.getClass(); //#1
   try {
     Method method = cls.getMethod("setColor", //#2
         new Class[] { Color.class });
     method.invoke(obj, new Object[] { color }); //#3
   } catch (NoSuchMethodException ex) { //#4
     throw new IllegalArgumentException(cls.getName()
         + " does not support" + "method setColor(:Color)");
   } catch (IllegalAccessException ex) { //#5
     throw new IllegalArgumentException(
         "Insufficient access permissions to call"
             + "setColor(:Color) in class " + cls.getName());
   } catch (InvocationTargetException ex) { //#6
     throw new RuntimeException(ex);
   }
 }
 //stop extract setObjectColor
 static public class Rabbit {
   public boolean setColorCalled = false;
   public void setColor(Color c) {
     setColorCalled = true;
   }
 }

}


 </source>
   
  
 
  



Returns attribute"s getter method. If the method not found then NoSuchMethodException will be thrown.

   <source lang="java">

import java.lang.reflect.Method; import java.util.HashSet; import java.util.List; import java.util.Set; /*

* JBoss, Home of Professional Open Source
* Copyright 2005, JBoss Inc., and individual contributors as indicated
* by the @authors tag. See the copyright.txt in the distribution for a
* full listing of individual contributors.
*
* This is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* This software 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
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this software; if not, write to the Free
* Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA, or see the FSF site: http://www.fsf.org.
*/

public class Main {

 /**
  * Returns attribute"s getter method. If the method not found then
  * NoSuchMethodException will be thrown.
  * 
  * @param cls
  *          the class the attribute belongs too
  * @param attr
  *          the attribute"s name
  * @return attribute"s getter method
  * @throws NoSuchMethodException
  *           if the getter was not found
  */
 public final static Method getAttributeGetter(Class cls, String attr)
     throws NoSuchMethodException {
   StringBuffer buf = new StringBuffer(attr.length() + 3);
   buf.append("get");
   if (Character.isLowerCase(attr.charAt(0))) {
     buf.append(Character.toUpperCase(attr.charAt(0))).append(attr.substring(1));
   } else {
     buf.append(attr);
   }
   try {
     return cls.getMethod(buf.toString(), (Class[]) null);
   } catch (NoSuchMethodException e) {
     buf.replace(0, 3, "is");
     return cls.getMethod(buf.toString(), (Class[]) null);
   }
 }

}

 </source>
   
  
 
  



Returns attribute"s setter method. If the method not found then NoSuchMethodException will be thrown.

   <source lang="java">

import java.lang.reflect.Method; import java.util.HashSet; import java.util.List; import java.util.Set; /*

* JBoss, Home of Professional Open Source
* Copyright 2005, JBoss Inc., and individual contributors as indicated
* by the @authors tag. See the copyright.txt in the distribution for a
* full listing of individual contributors.
*
* This is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* This software 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
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this software; if not, write to the Free
* Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA, or see the FSF site: http://www.fsf.org.
*/

public class Main {

 /**
  * Returns attribute"s setter method. If the method not found then
  * NoSuchMethodException will be thrown.
  * 
  * @param cls
  *          the class the attribute belongs to
  * @param attr
  *          the attribute"s name
  * @param type
  *          the attribute"s type
  * @return attribute"s setter method
  * @throws NoSuchMethodException
  *           if the setter was not found
  */
 public final static Method getAttributeSetter(Class cls, String attr, Class type)
     throws NoSuchMethodException {
   StringBuffer buf = new StringBuffer(attr.length() + 3);
   buf.append("set");
   if (Character.isLowerCase(attr.charAt(0))) {
     buf.append(Character.toUpperCase(attr.charAt(0))).append(attr.substring(1));
   } else {
     buf.append(attr);
   }
   return cls.getMethod(buf.toString(), new Class[] { type });
 }

}

 </source>
   
  
 
  



Uses reflection and JavaBeans introspection to

   <source lang="java">

/*

* Copyright (c) 2000 David Flanagan.  All rights reserved.
* This code is from the book Java Examples in a Nutshell, 2nd Edition.
* It is provided AS-IS, WITHOUT ANY WARRANTY either expressed or implied.
* You may study, use, and modify it for any non-commercial purpose.
* You may distribute it non-commercially as long as you retain this notice.
* For a commercial use license, or to purchase the book (recommended),
* visit http://www.davidflanagan.ru/javaexamples2.
*/

import java.awt.Color; import java.awt.ruponent; import java.awt.Font; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; import java.beans.BeanInfo; import java.beans.Introspector; import java.beans.PropertyDescriptor; import java.lang.reflect.Method; import java.util.Vector; import javax.swing.ButtonGroup; import javax.swing.JFrame; import javax.swing.JMenu; import javax.swing.JMenuBar; import javax.swing.JMenuItem; import javax.swing.JRadioButtonMenuItem; import javax.swing.JTabbedPane; import javax.swing.SwingUtilities; import javax.swing.UIManager; /**

* This class is a program that uses reflection and JavaBeans introspection to
* create a set of named components, set named properties on those components,
* and display them. It allows the user to view the components using any
* installed look-and-feel. It is intended as a simple way to experiment with
* AWT and Swing components, and to view a number of the other examples
* developed in this chapter. It also demonstrates frames, menus, and the
* JTabbedPane component.
*/

public class ShowComponent {

 // The main program
 public static void main(String[] args) {
   // Process the command line to get the components to display
   Vector components = getComponentsFromArgs(args);
   // Create a frame (a window) to display them in
   JFrame frame = new JFrame("ShowComponent");
   // Handle window close requests by exiting the VM
   frame.addWindowListener(new WindowAdapter() { // Anonymous inner class
         public void windowClosing(WindowEvent e) {
           System.exit(0);
         }
       });
   // Set up a menu system that allows the user to select the
   // look-and-feel of the component from a list of installed PLAFs
   JMenuBar menubar = new JMenuBar(); // Create a menubar
   frame.setJMenuBar(menubar); // Tell the frame to display it
   JMenu plafmenu = createPlafMenu(frame); // Create a menu
   menubar.add(plafmenu); // Add the menu to the menubar
   // Create a JTabbedPane to display each of the components
   JTabbedPane pane = new JTabbedPane();
   // Now add each component as a tab of the tabbed pane
   // Use the unqualified component classname as the tab text
   for (int i = 0; i < components.size(); i++) {
     Component c = (Component) components.elementAt(i);
     String classname = c.getClass().getName();
     String tabname = classname
         .substring(classname.lastIndexOf(".") + 1);
     pane.addTab(tabname, c);
   }
   // Add the tabbed pane to the frame. Note the call to getContentPane()
   // This is required for JFrame, but not for most Swing components
   frame.getContentPane().add(pane);
   // Set the frame size and pop it up
   frame.pack(); // Make frame as big as its kids need
   frame.setVisible(true); // Make the frame visible on the screen
   // The main() method exits now but the Java VM keeps running because
   // all AWT programs automatically start an event-handling thread.
 }
 /**
  * This static method queries the system to find out what Pluggable
  * Look-and-Feel (PLAF) implementations are available. Then it creates a
  * JMenu component that lists each of the implementations by name and allows
  * the user to select one of them using JRadioButtonMenuItem components.
  * When the user selects one, the selected menu item traverses the component
  * hierarchy and tells all components to use the new PLAF.
  */
 public static JMenu createPlafMenu(final JFrame frame) {
   // Create the menu
   JMenu plafmenu = new JMenu("Look and Feel");
   // Create an object used for radio button mutual exclusion
   ButtonGroup radiogroup = new ButtonGroup();
   // Look up the available look and feels
   UIManager.LookAndFeelInfo[] plafs = UIManager
       .getInstalledLookAndFeels();
   // Loop through the plafs, and add a menu item for each one
   for (int i = 0; i < plafs.length; i++) {
     String plafName = plafs[i].getName();
     final String plafClassName = plafs[i].getClassName();
     // Create the menu item
     JMenuItem item = plafmenu.add(new JRadioButtonMenuItem(plafName));
     // Tell the menu item what to do when it is selected
     item.addActionListener(new ActionListener() {
       public void actionPerformed(ActionEvent e) {
         try {
           // Set the new look and feel
           UIManager.setLookAndFeel(plafClassName);
           // Tell each component to change its look-and-feel
           SwingUtilities.updateComponentTreeUI(frame);
           // Tell the frame to resize itself to the its
           // children"s new desired sizes
           frame.pack();
         } catch (Exception ex) {
           System.err.println(ex);
         }
       }
     });
     // Only allow one menu item to be selected at once
     radiogroup.add(item);
   }
   return plafmenu;
 }
 /**
  * This method loops through the command line arguments looking for class
  * names of components to create and property settings for those components
  * in the form name=value. This method demonstrates reflection and JavaBeans
  * introspection as they can be applied to dynamically created GUIs
  */
 public static Vector getComponentsFromArgs(String[] args) {
   Vector components = new Vector(); // List of components to return
   Component component = null; // The current component
   PropertyDescriptor[] properties = null; // Properties of the component
   Object[] methodArgs = new Object[1]; // We"ll use this below
   nextarg: // This is a labeled loop
   for (int i = 0; i < args.length; i++) { // Loop through all arguments
     // If the argument does not contain an equal sign, then it is
     // a component class name. Otherwise it is a property setting
     int equalsPos = args[i].indexOf("=");
     if (equalsPos == -1) { // Its the name of a component
       try {
         // Load the named component class
         Class componentClass = Class.forName(args[i]);
         // Instantiate it to create the component instance
         component = (Component) componentClass.newInstance();
         // Use JavaBeans to introspect the component
         // And get the list of properties it supports
         BeanInfo componentBeanInfo = Introspector
             .getBeanInfo(componentClass);
         properties = componentBeanInfo.getPropertyDescriptors();
       } catch (Exception e) {
         // If any step failed, print an error and exit
         System.out.println("Can"t load, instantiate, "
             + "or introspect: " + args[i]);
         System.exit(1);
       }
       // If we succeeded, store the component in the vector
       components.addElement(component);
     } else { // The arg is a name=value property specification
       String name = args[i].substring(0, equalsPos); // property name
       String value = args[i].substring(equalsPos + 1); // property
                                // value
       // If we don"t have a component to set this property on, skip!
       if (component == null)
         continue nextarg;
       // Now look through the properties descriptors for this
       // component to find one with the same name.
       for (int p = 0; p < properties.length; p++) {
         if (properties[p].getName().equals(name)) {
           // Okay, we found a property of the right name.
           // Now get its type, and the setter method
           Class type = properties[p].getPropertyType();
           Method setter = properties[p].getWriteMethod();
           // Check if property is read-only!
           if (setter == null) {
             System.err.println("Property " + name
                 + " is read-only");
             continue nextarg; // continue with next argument
           }
           // Try to convert the property value to the right type
           // We support a small set of common property types here
           // Store the converted value in an Object[] so it can
           // be easily passed when we invoke the property setter
           try {
             if (type == String.class) { // no conversion needed
               methodArgs[0] = value;
             } else if (type == int.class) { // String to int
               methodArgs[0] = Integer.valueOf(value);
             } else if (type == boolean.class) { // to boolean
               methodArgs[0] = Boolean.valueOf(value);
             } else if (type == Color.class) { // to Color
               methodArgs[0] = Color.decode(value);
             } else if (type == Font.class) { // String to Font
               methodArgs[0] = Font.decode(value);
             } else {
               // If we can"t convert, ignore the property
               System.err.println("Property " + name
                   + " is of unsupported type "
                   + type.getName());
               continue nextarg;
             }
           } catch (Exception e) {
             // If conversion failed, continue with the next arg
             System.err.println("Can"t convert  "" + value
                 + "" to type " + type.getName()
                 + " for property " + name);
             continue nextarg;
           }
           // Finally, use reflection to invoke the property
           // setter method of the component we created, and pass
           // in the converted property value.
           try {
             setter.invoke(component, methodArgs);
           } catch (Exception e) {
             System.err.println("Can"t set property: " + name);
           }
           // Now go on to next command-line arg
           continue nextarg;
         }
       }
       // If we get here, we didn"t find the named property
       System.err.println("Warning: No such property: " + name);
     }
   }
   return components;
 }

}


 </source>