1. /*
  2. * @(#)StateEdit.java 1.10 00/02/02
  3. *
  4. * Copyright 1997-2000 Sun Microsystems, Inc. All Rights Reserved.
  5. *
  6. * This software is the proprietary information of Sun Microsystems, Inc.
  7. * Use is subject to license terms.
  8. *
  9. */
  10. package javax.swing.undo;
  11. import java.util.Enumeration;
  12. import java.util.Hashtable;
  13. import java.util.Vector;
  14. /**
  15. * <P>StateEdit is a general edit for objects that change state.
  16. * Objects being edited must conform to the StateEditable interface.</P>
  17. *
  18. * <P>This edit class works by asking an object to store it's state in
  19. * Hashtables before and after editing occurs. Upon undo or redo the
  20. * object is told to restore it's state from these Hashtables.</P>
  21. *
  22. * A state edit is used as follows:
  23. * <PRE>
  24. * // Create the edit during the "before" state of the object
  25. * StateEdit newEdit = new StateEdit(myObject);
  26. * // Modify the object
  27. * myObject.someStateModifyingMethod();
  28. * // "end" the edit when you are done modifying the object
  29. * newEdit.end();
  30. * </PRE>
  31. *
  32. * <P><EM>Note that when a StateEdit ends, it removes redundant state from
  33. * the Hashtables - A state Hashtable is not guaranteed to contain all
  34. * keys/values placed into it when the state is stored!</EM></P>
  35. *
  36. * @see StateEditable
  37. *
  38. * @version 1.10 02/02/00
  39. * @author Ray Ryan
  40. */
  41. public class StateEdit
  42. extends AbstractUndoableEdit {
  43. protected static final String RCSID = "$Id: StateEdit.java,v 1.6 1997/10/01 20:05:51 sandipc Exp $";
  44. //
  45. // Attributes
  46. //
  47. /**
  48. * The object being edited
  49. */
  50. protected StateEditable object;
  51. /**
  52. * The state information prior to the edit
  53. */
  54. protected Hashtable preState;
  55. /**
  56. * The state information after the edit
  57. */
  58. protected Hashtable postState;
  59. /**
  60. * The undo/redo presentation name
  61. */
  62. protected String undoRedoName;
  63. //
  64. // Constructors
  65. //
  66. /**
  67. * Create and return a new StateEdit.
  68. *
  69. * @param anObject The object to watch for changing state
  70. *
  71. * @see StateEdit
  72. */
  73. public StateEdit(StateEditable anObject) {
  74. super();
  75. init (anObject,null);
  76. }
  77. /**
  78. * Create and return a new StateEdit with a presentation name.
  79. *
  80. * @param anObject The object to watch for changing state
  81. * @param name The presentation name to be used for this edit
  82. *
  83. * @see StateEdit
  84. */
  85. public StateEdit(StateEditable anObject, String name) {
  86. super();
  87. init (anObject,name);
  88. }
  89. protected void init (StateEditable anObject, String name) {
  90. this.object = anObject;
  91. this.preState = new Hashtable(11);
  92. this.object.storeState(this.preState);
  93. this.postState = null;
  94. this.undoRedoName = name;
  95. }
  96. //
  97. // Operation
  98. //
  99. /**
  100. * Gets the post-edit state of the StateEditable object and
  101. * ends the edit.
  102. */
  103. public void end() {
  104. this.postState = new Hashtable(11);
  105. this.object.storeState(this.postState);
  106. this.removeRedundantState();
  107. }
  108. /**
  109. * Tells the edited object to apply the state prior to the edit
  110. */
  111. public void undo() {
  112. super.undo();
  113. this.object.restoreState(preState);
  114. }
  115. /**
  116. * Tells the edited object to apply the state after the edit
  117. */
  118. public void redo() {
  119. super.redo();
  120. this.object.restoreState(postState);
  121. }
  122. /**
  123. * Gets the presentation name for this edit
  124. */
  125. public String getPresentationName() {
  126. return this.undoRedoName;
  127. }
  128. //
  129. // Internal support
  130. //
  131. /**
  132. * Remove redundant key/values in state hashtables.
  133. */
  134. protected void removeRedundantState() {
  135. Vector uselessKeys = new Vector();
  136. Enumeration myKeys = preState.keys();
  137. // Locate redundant state
  138. while (myKeys.hasMoreElements()) {
  139. Object myKey = myKeys.nextElement();
  140. if (postState.containsKey(myKey) &&
  141. postState.get(myKey).equals(preState.get(myKey))) {
  142. uselessKeys.addElement(myKey);
  143. }
  144. }
  145. // Remove redundant state
  146. for (int i = uselessKeys.size()-1; i >= 0; i--) {
  147. Object myKey = uselessKeys.elementAt(i);
  148. preState.remove(myKey);
  149. postState.remove(myKey);
  150. }
  151. }
  152. } // End of class StateEdit