1. /*
  2. * @(#)FeatureDescriptor.java 1.33 04/05/05
  3. *
  4. * Copyright 2004 Sun Microsystems, Inc. All rights reserved.
  5. * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
  6. */
  7. package java.beans;
  8. import java.lang.ref.Reference;
  9. import java.lang.ref.WeakReference;
  10. import java.lang.ref.SoftReference;
  11. /**
  12. * The FeatureDescriptor class is the common baseclass for PropertyDescriptor,
  13. * EventSetDescriptor, and MethodDescriptor, etc.
  14. * <p>
  15. * It supports some common information that can be set and retrieved for
  16. * any of the introspection descriptors.
  17. * <p>
  18. * In addition it provides an extension mechanism so that arbitrary
  19. * attribute/value pairs can be associated with a design feature.
  20. */
  21. public class FeatureDescriptor {
  22. private Reference classRef;
  23. /**
  24. * Constructs a <code>FeatureDescriptor</code>.
  25. */
  26. public FeatureDescriptor() {
  27. }
  28. /**
  29. * Gets the programmatic name of this feature.
  30. *
  31. * @return The programmatic name of the property/method/event
  32. */
  33. public String getName() {
  34. return name;
  35. }
  36. /**
  37. * Sets the programmatic name of this feature.
  38. *
  39. * @param name The programmatic name of the property/method/event
  40. */
  41. public void setName(String name) {
  42. this.name = name;
  43. }
  44. /**
  45. * Gets the localized display name of this feature.
  46. *
  47. * @return The localized display name for the property/method/event.
  48. * This defaults to the same as its programmatic name from getName.
  49. */
  50. public String getDisplayName() {
  51. if (displayName == null) {
  52. return getName();
  53. }
  54. return displayName;
  55. }
  56. /**
  57. * Sets the localized display name of this feature.
  58. *
  59. * @param displayName The localized display name for the
  60. * property/method/event.
  61. */
  62. public void setDisplayName(String displayName) {
  63. this.displayName = displayName;
  64. }
  65. /**
  66. * The "expert" flag is used to distinguish between those features that are
  67. * intended for expert users from those that are intended for normal users.
  68. *
  69. * @return True if this feature is intended for use by experts only.
  70. */
  71. public boolean isExpert() {
  72. return expert;
  73. }
  74. /**
  75. * The "expert" flag is used to distinguish between features that are
  76. * intended for expert users from those that are intended for normal users.
  77. *
  78. * @param expert True if this feature is intended for use by experts only.
  79. */
  80. public void setExpert(boolean expert) {
  81. this.expert = expert;
  82. }
  83. /**
  84. * The "hidden" flag is used to identify features that are intended only
  85. * for tool use, and which should not be exposed to humans.
  86. *
  87. * @return True if this feature should be hidden from human users.
  88. */
  89. public boolean isHidden() {
  90. return hidden;
  91. }
  92. /**
  93. * The "hidden" flag is used to identify features that are intended only
  94. * for tool use, and which should not be exposed to humans.
  95. *
  96. * @param hidden True if this feature should be hidden from human users.
  97. */
  98. public void setHidden(boolean hidden) {
  99. this.hidden = hidden;
  100. }
  101. /**
  102. * The "preferred" flag is used to identify features that are particularly
  103. * important for presenting to humans.
  104. *
  105. * @return True if this feature should be preferentially shown to human users.
  106. */
  107. public boolean isPreferred() {
  108. return preferred;
  109. }
  110. /**
  111. * The "preferred" flag is used to identify features that are particularly
  112. * important for presenting to humans.
  113. *
  114. * @param preferred True if this feature should be preferentially shown
  115. * to human users.
  116. */
  117. public void setPreferred(boolean preferred) {
  118. this.preferred = preferred;
  119. }
  120. /**
  121. * Gets the short description of this feature.
  122. *
  123. * @return A localized short description associated with this
  124. * property/method/event. This defaults to be the display name.
  125. */
  126. public String getShortDescription() {
  127. if (shortDescription == null) {
  128. return getDisplayName();
  129. }
  130. return shortDescription;
  131. }
  132. /**
  133. * You can associate a short descriptive string with a feature. Normally
  134. * these descriptive strings should be less than about 40 characters.
  135. * @param text A (localized) short description to be associated with
  136. * this property/method/event.
  137. */
  138. public void setShortDescription(String text) {
  139. shortDescription = text;
  140. }
  141. /**
  142. * Associate a named attribute with this feature.
  143. *
  144. * @param attributeName The locale-independent name of the attribute
  145. * @param value The value.
  146. */
  147. public void setValue(String attributeName, Object value) {
  148. if (table == null) {
  149. table = new java.util.Hashtable();
  150. }
  151. table.put(attributeName, value);
  152. }
  153. /**
  154. * Retrieve a named attribute with this feature.
  155. *
  156. * @param attributeName The locale-independent name of the attribute
  157. * @return The value of the attribute. May be null if
  158. * the attribute is unknown.
  159. */
  160. public Object getValue(String attributeName) {
  161. if (table == null) {
  162. return null;
  163. }
  164. return table.get(attributeName);
  165. }
  166. /**
  167. * Gets an enumeration of the locale-independent names of this
  168. * feature.
  169. *
  170. * @return An enumeration of the locale-independent names of any
  171. * attributes that have been registered with setValue.
  172. */
  173. public java.util.Enumeration<String> attributeNames() {
  174. if (table == null) {
  175. table = new java.util.Hashtable();
  176. }
  177. return table.keys();
  178. }
  179. /**
  180. * Package-private constructor,
  181. * Merge information from two FeatureDescriptors.
  182. * The merged hidden and expert flags are formed by or-ing the values.
  183. * In the event of other conflicts, the second argument (y) is
  184. * given priority over the first argument (x).
  185. *
  186. * @param x The first (lower priority) MethodDescriptor
  187. * @param y The second (higher priority) MethodDescriptor
  188. */
  189. FeatureDescriptor(FeatureDescriptor x, FeatureDescriptor y) {
  190. expert = x.expert | y.expert;
  191. hidden = x.hidden | y.hidden;
  192. preferred = x.preferred | y.preferred;
  193. name = y.name;
  194. shortDescription = x.shortDescription;
  195. if (y.shortDescription != null) {
  196. shortDescription = y.shortDescription;
  197. }
  198. displayName = x.displayName;
  199. if (y.displayName != null) {
  200. displayName = y.displayName;
  201. }
  202. classRef = x.classRef;
  203. if (y.classRef != null) {
  204. classRef = y.classRef;
  205. }
  206. addTable(x.table);
  207. addTable(y.table);
  208. }
  209. /*
  210. * Package-private dup constructor
  211. * This must isolate the new object from any changes to the old object.
  212. */
  213. FeatureDescriptor(FeatureDescriptor old) {
  214. expert = old.expert;
  215. hidden = old.hidden;
  216. preferred = old.preferred;
  217. name = old.name;
  218. shortDescription = old.shortDescription;
  219. displayName = old.displayName;
  220. classRef = old.classRef;
  221. addTable(old.table);
  222. }
  223. private void addTable(java.util.Hashtable t) {
  224. if (t == null) {
  225. return;
  226. }
  227. java.util.Enumeration keys = t.keys();
  228. while (keys.hasMoreElements()) {
  229. String key = (String)keys.nextElement();
  230. Object value = t.get(key);
  231. setValue(key, value);
  232. }
  233. }
  234. // Package private methods for recreating the weak/soft referent
  235. void setClass0(Class cls) {
  236. classRef = createReference(cls);
  237. }
  238. Class getClass0() {
  239. return (Class)getObject(classRef);
  240. }
  241. /**
  242. * Create a Reference wrapper for the object.
  243. *
  244. * @param obj object that will be wrapped
  245. * @param soft true if a SoftReference should be created; otherwise Soft
  246. * @return a Reference or null if obj is null.
  247. */
  248. static Reference createReference(Object obj, boolean soft) {
  249. Reference ref = null;
  250. if (obj != null) {
  251. if (soft) {
  252. ref = new SoftReference(obj);
  253. } else {
  254. ref = new WeakReference(obj);
  255. }
  256. }
  257. return ref;
  258. }
  259. // Convenience method which creates a WeakReference.
  260. static Reference createReference(Object obj) {
  261. return createReference(obj, false);
  262. }
  263. /**
  264. * Returns an object from a Reference wrapper.
  265. *
  266. * @return the Object in a wrapper or null.
  267. */
  268. static Object getObject(Reference ref) {
  269. return (ref == null) ? null : (Object)ref.get();
  270. }
  271. static String capitalize(String s) {
  272. return NameGenerator.capitalize(s);
  273. }
  274. private boolean expert;
  275. private boolean hidden;
  276. private boolean preferred;
  277. private String shortDescription;
  278. private String name;
  279. private String displayName;
  280. private java.util.Hashtable table;
  281. }