You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cayenne.apache.org by an...@apache.org on 2009/12/09 15:12:36 UTC

svn commit: r888809 [1/2] - in /cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne: modeler/ modeler/action/ modeler/dialog/ modeler/editor/ modeler/editor/datanode/ modeler/undo/ modeler/util/ swing/ swing/comp...

Author: andrey
Date: Wed Dec  9 14:12:35 2009
New Revision: 888809

URL: http://svn.apache.org/viewvc?rev=888809&view=rev
Log:
CAY-1191 Undo/Redo support in modeler

Added:
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/DbEntitySyncUndoableEdit.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/JEditTextAreaUndoableAdapter.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/TextCompoundEdit.java
Removed:
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneCompoundEdit.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/util/JTextFieldUndoable.java
Modified:
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/Application.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/ProjectTreeView.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/action/DbEntitySyncAction.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/dialog/ResolveDbRelationshipDialog.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/EditorView.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/EjbqlQueryScriptsTab.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/SQLTemplateScriptsTab.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/AdapterView.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/CustomDataSourceView.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/DBCPDataSourceView.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/JDBCDataSourceView.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/JNDIDataSourceView.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/MainDataNodeView.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/PasswordEncoderView.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/AddPrefetchUndoableEdit.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneTableModelUndoableEdit.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneUndoManager.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneUndoableEdit.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CreateAttributeUndoableEdit.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CreateRelationshipUndoableEdit.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/InferRelationshipsUndoableEdit.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/JTextFieldUndoListener.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/RelationshipUndoableEdit.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/RemoveAttributeUndoableEdit.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/RemoveCompoundUndoableEdit.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/RemoveRelationshipUndoableEdit.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/util/CayenneWidgetFactory.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/util/TextAdapter.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/swing/BindingBuilder.java
    cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/swing/components/textpane/JCayenneTextPane.java

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/Application.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/Application.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/Application.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/Application.java Wed Dec  9 14:12:35 2009
@@ -32,6 +32,7 @@
 import javax.swing.undo.UndoManager;
 
 import org.apache.cayenne.modeler.dialog.LogConsole;
+import org.apache.cayenne.modeler.undo.CayenneUndoManager;
 import org.apache.cayenne.modeler.util.AdapterMapping;
 import org.apache.cayenne.modeler.util.CayenneAction;
 import org.apache.cayenne.modeler.util.CayenneDialog;
@@ -86,7 +87,7 @@
     protected BindingFactory bindingFactory;
     protected AdapterMapping adapterMapping;
     
-    protected UndoManager undoManager;
+    protected CayenneUndoManager undoManager;
 
     // This is for OS X support
     private boolean isQuittingApplication = false;
@@ -153,7 +154,7 @@
     /**
      * Returns undo-edits controller.
      */
-    public UndoManager getUndoManager() {
+    public CayenneUndoManager getUndoManager() {
         return undoManager;
     }
 

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/ProjectTreeView.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/ProjectTreeView.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/ProjectTreeView.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/ProjectTreeView.java Wed Dec  9 14:12:35 2009
@@ -172,6 +172,7 @@
         };
 
         addTreeSelectionListener(treeSelectionListener);
+        addTreeSelectionListener(mediator.getApplication().getUndoManager());
 
         addMouseListener(new PopupHandler());
 

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/action/DbEntitySyncAction.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/action/DbEntitySyncAction.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/action/DbEntitySyncAction.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/action/DbEntitySyncAction.java Wed Dec  9 14:12:35 2009
@@ -29,6 +29,7 @@
 import org.apache.cayenne.modeler.Application;
 import org.apache.cayenne.modeler.ProjectController;
 import org.apache.cayenne.modeler.dialog.objentity.EntitySyncController;
+import org.apache.cayenne.modeler.undo.DbEntitySyncUndoableEdit;
 import org.apache.cayenne.modeler.util.CayenneAction;
 import org.apache.cayenne.project.ProjectPath;
 import org.apache.cayenne.util.EntityMergeSupport;
@@ -79,15 +80,34 @@
                 return;
             }
 
+            DbEntitySyncUndoableEdit undoableEdit = new DbEntitySyncUndoableEdit(mediator
+                    .getCurrentDataDomain(), mediator.getCurrentDataMap());
+
             while (it.hasNext()) {
                 ObjEntity entity = (ObjEntity) it.next();
+
+                DbEntitySyncUndoableEdit.EntitySyncUndoableListener listener = undoableEdit.new EntitySyncUndoableListener(
+                        entity);
+
+                merger.addEntityMergeListener(listener);
+
+                if (merger.isRemoveMeaningfulFKs()) {
+                    undoableEdit.addEdit(undoableEdit.new MeaningfulFKsUndoableEdit(
+                            entity,
+                            merger.getMeaningfulFKs(entity)));
+                }
+
                 if (merger.synchronizeWithDbEntity(entity)) {
                     mediator.fireObjEntityEvent(new EntityEvent(
                             this,
                             entity,
                             MapEvent.CHANGE));
                 }
+
+                merger.removeEntityMergeListener(listener);
             }
+
+            application.getUndoManager().addEdit(undoableEdit);
         }
     }
 

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/dialog/ResolveDbRelationshipDialog.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/dialog/ResolveDbRelationshipDialog.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/dialog/ResolveDbRelationshipDialog.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/dialog/ResolveDbRelationshipDialog.java Wed Dec  9 14:12:35 2009
@@ -67,390 +67,384 @@
  */
 public class ResolveDbRelationshipDialog extends CayenneDialog {
 
-	
-	protected DbRelationship relationship;
-	protected DbRelationship reverseRelationship;
-
-	protected JTextField name;
-	protected JTextField reverseName;
-	protected CayenneTable table;
-	protected JButton addButton;
-	protected JButton removeButton;
-	protected JButton saveButton;
-	protected JButton cancelButton;
-
-	private boolean cancelPressed;
-
-	private RelationshipUndoableEdit undo;
-
-	private boolean editable = true;
-
-	public ResolveDbRelationshipDialog(DbRelationship relationship) {
-		this(relationship, true);
-	}
-
-	public ResolveDbRelationshipDialog(DbRelationship relationship,
-			boolean editable) {
-		super(Application.getFrame(), "", true);
-		this.editable = editable;
-
-		initView();
-		initController();
-		initWithModel(relationship);
-
-		this.undo = new RelationshipUndoableEdit(relationship);
-
-		this.pack();
-		this.centerWindow();
-
-	}
-
-	/**
-	 * Creates graphical components.
-	 */
-	private void initView() {
-
-		// create widgets
-		name = CayenneWidgetFactory.createTextField(25);
-		reverseName = CayenneWidgetFactory.createTextField(25);
-
-		addButton = new JButton("Add");
-		addButton.setEnabled(this.editable);
-		
-		removeButton = new JButton("Remove");
-		removeButton.setEnabled(this.editable);
-		
-		saveButton = new JButton("Done");
-		
-		cancelButton = new JButton("Cancel");
-		cancelButton.setEnabled(this.editable);
-
-		table = new AttributeTable();
-		table.getSelectionModel().setSelectionMode(
-				ListSelectionModel.SINGLE_SELECTION);
-
-		// assemble
-		getContentPane().setLayout(new BorderLayout());
-
-		CellConstraints cc = new CellConstraints();
-		PanelBuilder builder = new PanelBuilder(
-				new FormLayout(
-						"right:max(50dlu;pref), 3dlu, fill:min(150dlu;pref), 3dlu, fill:min(50dlu;pref)",
-						"p, 3dlu, p, 3dlu, p, 9dlu, p, 3dlu, top:14dlu, 3dlu, top:p:grow"));
-		builder.setDefaultDialogBorder();
-
-		builder.addSeparator("DbRelationship Information", cc.xywh(1, 1, 5, 1));
-		builder.addLabel("Relationship:", cc.xy(1, 3));
-		builder.add(name, cc.xywh(3, 3, 1, 1));
-		builder.addLabel("Reverse Relationship", cc.xy(1, 5));
-		builder.add(reverseName, cc.xywh(3, 5, 1, 1));
-
-		builder.addSeparator("Joins", cc.xywh(1, 7, 5, 1));
-		builder.add(new JScrollPane(table), cc.xywh(1, 9, 3, 3, "fill, fill"));
-
-		JPanel buttons = new JPanel(new FlowLayout(FlowLayout.LEADING));
-
-		buttons.add(addButton);
-		buttons.add(removeButton);
-
-		builder.add(buttons, cc.xywh(5, 9, 1, 3));
-
-		getContentPane().add(builder.getPanel(), BorderLayout.CENTER);
-		getContentPane().add(
-				PanelFactory.createButtonPanel(new JButton[] { saveButton,
-						cancelButton }), BorderLayout.SOUTH);
-	}
-
-	private void initWithModel(DbRelationship aRelationship) {
-		// sanity check
-		if (aRelationship.getSourceEntity() == null) {
-			throw new CayenneRuntimeException("Null source entity: "
-					+ aRelationship);
-		}
-
-		if (aRelationship.getTargetEntity() == null) {
-			throw new CayenneRuntimeException("Null target entity: "
-					+ aRelationship);
-		}
-
-		if (aRelationship.getSourceEntity().getDataMap() == null) {
-			throw new CayenneRuntimeException("Null DataMap: "
-					+ aRelationship.getSourceEntity());
-		}
-
-		// Once assigned, can reference relationship directly. Would it be
-		// OK to assign relationship at the very top of this method?
-		relationship = aRelationship;
-		reverseRelationship = relationship.getReverseRelationship();
-
-		// init UI components
-		setTitle("DbRelationship Info: "
-				+ relationship.getSourceEntity().getName() + " to "
-				+ relationship.getTargetEntityName());
-
-		table.setModel(new DbJoinTableModel(relationship, getMediator(), this,
-				true));
-		TableColumn sourceColumn = table.getColumnModel().getColumn(
-				DbJoinTableModel.SOURCE);
-		sourceColumn.setMinWidth(150);
-		JComboBox comboBox = CayenneWidgetFactory.createComboBox(ModelerUtil
-				.getDbAttributeNames(getMediator(), (DbEntity) relationship
-						.getSourceEntity()), true);
-
-		AutoCompletion.enable(comboBox);
-		sourceColumn.setCellEditor(CayenneWidgetFactory
-				.createCellEditor(comboBox));
-
-		TableColumn targetColumn = table.getColumnModel().getColumn(
-				DbJoinTableModel.TARGET);
-		targetColumn.setMinWidth(150);
-		comboBox = CayenneWidgetFactory.createComboBox(ModelerUtil
-				.getDbAttributeNames(getMediator(), (DbEntity) relationship
-						.getTargetEntity()), true);
-		AutoCompletion.enable(comboBox);
-
-		targetColumn.setCellEditor(CayenneWidgetFactory
-				.createCellEditor(comboBox));
-
-		if (reverseRelationship != null) {
-			reverseName.setText(reverseRelationship.getName());
-		}
-
-		name.setText(relationship.getName());
-	}
-
-	private void initController() {
-		addButton.addActionListener(new ActionListener() {
-
-			public void actionPerformed(ActionEvent e) {
-				DbJoinTableModel model = (DbJoinTableModel) table.getModel();
-
-				DbJoin join = new DbJoin(relationship);
-				model.addRow(join);
-
-				undo.addDbJoinAddUndo(join);
-
-				table.select(model.getRowCount() - 1);
-			}
-		});
-
-		removeButton.addActionListener(new ActionListener() {
-
-			public void actionPerformed(ActionEvent e) {
-				DbJoinTableModel model = (DbJoinTableModel) table.getModel();
-				stopEditing();
-				int row = table.getSelectedRow();
-
-				DbJoin join = model.getJoin(row);
-				undo.addDbJoinRemoveUndo(join);
-
-				model.removeRow(join);
-			}
-		});
-
-		saveButton.addActionListener(new ActionListener() {
-
-			public void actionPerformed(ActionEvent e) {
-				cancelPressed = false;
-				
-				if (editable) {
-					save();
-				}
-				
-				dispose();
-			}
-		});
-
-		cancelButton.addActionListener(new ActionListener() {
-
-			public void actionPerformed(ActionEvent e) {
-				cancelPressed = true;
-				setVisible(false);
-			}
-		});
-	}
-
-	public boolean isCancelPressed() {
-		return cancelPressed;
-	}
-
-	private void stopEditing() {
-		// Stop whatever editing may be taking place
-		int col_index = table.getEditingColumn();
-		if (col_index >= 0) {
-			TableColumn col = table.getColumnModel().getColumn(col_index);
-			col.getCellEditor().stopCellEditing();
-		}
-	}
-
-	private void save() {
-
-		// extract names...
-		String sourceEntityName = name.getText();
-		if (sourceEntityName.length() == 0) {
-			sourceEntityName = null;
-		}
-
-		if (sourceEntityName == null) {
-			sourceEntityName = NamedObjectFactory.createName(
-					DbRelationship.class, relationship.getSourceEntity());
-		}
-
-		if (!validateName(relationship.getSourceEntity(), relationship,
-				sourceEntityName)) {
-			return;
-		}
-
-		String targetEntityName = reverseName.getText().trim();
-		if (targetEntityName.length() == 0) {
-			targetEntityName = null;
-		}
-
-		if (targetEntityName == null) {
-			targetEntityName = NamedObjectFactory.createName(
-					DbRelationship.class, relationship.getTargetEntity());
-		}
-
-		// check if reverse name is valid
-		DbJoinTableModel model = (DbJoinTableModel) table.getModel();
-		boolean updatingReverse = model.getObjectList().size() > 0;
-
-		if (updatingReverse
-				&& !validateName(relationship.getTargetEntity(),
-						reverseRelationship, targetEntityName)) {
-			return;
-		}
-
-		// handle name update
-		if (!Util.nullSafeEquals(sourceEntityName, relationship.getName())) {
-			String oldName = relationship.getName();
-
-			ProjectUtil.setRelationshipName(relationship.getSourceEntity(),
-					relationship, sourceEntityName);
-
-			undo.addNameUndo(relationship, oldName, sourceEntityName);
-
-			getMediator().fireDbRelationshipEvent(
-					new RelationshipEvent(this, relationship, relationship
-							.getSourceEntity(), oldName));
-		}
-
-		model.commit();
-
-		// check "to dep pk" setting,
-		// maybe this is no longer valid
-		if (relationship.isToDependentPK() && !relationship.isValidForDepPk()) {
-			relationship.setToDependentPK(false);
-		}
-
-		// If new reverse DbRelationship was created, add it to the target
-		// Don't create reverse with no joins - makes no sense...
-		if (updatingReverse) {
-
-			// If didn't find anything, create reverseDbRel
-			if (reverseRelationship == null) {
-				reverseRelationship = new DbRelationship(targetEntityName);
-				reverseRelationship.setSourceEntity(relationship
-						.getTargetEntity());
-				reverseRelationship.setTargetEntity(relationship
-						.getSourceEntity());
-				reverseRelationship.setToMany(!relationship.isToMany());
-				relationship.getTargetEntity().addRelationship(
-						reverseRelationship);
-
-				// fire only if the relationship is to the same entity...
-				// this is needed to update entity view...
-				if (relationship.getSourceEntity() == relationship
-						.getTargetEntity()) {
-					getMediator().fireDbRelationshipEvent(
-							new RelationshipEvent(this, reverseRelationship,
-									reverseRelationship.getSourceEntity(),
-									MapEvent.ADD));
-				}
-			} else if (!Util.nullSafeEquals(targetEntityName,
-					reverseRelationship.getName())) {
-
-				String oldName = reverseRelationship.getName();
-
-				ProjectUtil.setRelationshipName(reverseRelationship
-						.getSourceEntity(), reverseRelationship,
-						targetEntityName);
-
-				undo
-						.addNameUndo(reverseRelationship, oldName,
-								targetEntityName);
-
-				getMediator()
-						.fireDbRelationshipEvent(
-								new RelationshipEvent(this,
-										reverseRelationship,
-										reverseRelationship.getSourceEntity(),
-										oldName));
-			}
-
-			Collection reverseJoins = getReverseJoins();
-			reverseRelationship.setJoins(reverseJoins);
-
-			// check if joins map to a primary key of this entity
-			if (!relationship.isToDependentPK()
-					&& reverseRelationship.isValidForDepPk()) {
-				reverseRelationship.setToDependentPK(true);
-			}
-		}
-
-		if (undo.hasEdits()) {
-			Application.getInstance().getUndoManager().addEdit(undo);
-		}
-
-		getMediator().fireDbRelationshipEvent(
-				new RelationshipEvent(this, relationship, relationship
-						.getSourceEntity()));
-	}
-
-	private boolean validateName(Entity entity, Relationship aRelationship,
-			String newName) {
-		Relationship existing = entity.getRelationship(newName);
-		if (existing != null
-				&& (aRelationship == null || aRelationship != existing)) {
-			JOptionPane.showMessageDialog(this,
-					"There is an existing relationship named \"" + newName
-							+ "\". Select a different name.");
-			return false;
-		}
-
-		return true;
-	}
-
-	private Collection getReverseJoins() {
-		Collection<DbJoin> joins = relationship.getJoins();
-
-		if ((joins == null) || (joins.size() == 0)) {
-			return Collections.EMPTY_LIST;
-		}
-
-		List reverseJoins = new ArrayList(joins.size());
-
-		// Loop through the list of attribute pairs, create reverse pairs
-		// and put them to the reverse list.
-		for (DbJoin pair : joins) {
-			DbJoin reverseJoin = pair.createReverseJoin();
-
-			// since reverse relationship is not yet initialized,
-			// reverse join will not have it set automatically
-			reverseJoin.setRelationship(reverseRelationship);
-			reverseJoins.add(reverseJoin);
-		}
-
-		return reverseJoins;
-	}
-
-	final class AttributeTable extends CayenneTable {
-
-		final Dimension preferredSize = new Dimension(203, 100);
-
-		@Override
-		public Dimension getPreferredScrollableViewportSize() {
-			return preferredSize;
-		}
-	}
+    protected DbRelationship relationship;
+    protected DbRelationship reverseRelationship;
+
+    protected JTextField name;
+    protected JTextField reverseName;
+    protected CayenneTable table;
+    protected JButton addButton;
+    protected JButton removeButton;
+    protected JButton saveButton;
+    protected JButton cancelButton;
+
+    private boolean cancelPressed;
+
+    private RelationshipUndoableEdit undo;
+
+    private boolean editable = true;
+
+    public ResolveDbRelationshipDialog(DbRelationship relationship) {
+        this(relationship, true);
+    }
+
+    public ResolveDbRelationshipDialog(DbRelationship relationship, boolean editable) {
+        super(Application.getFrame(), "", true);
+        this.editable = editable;
+
+        initView();
+        initController();
+        initWithModel(relationship);
+
+        this.undo = new RelationshipUndoableEdit(relationship);
+
+        this.pack();
+        this.centerWindow();
+
+    }
+
+    /**
+     * Creates graphical components.
+     */
+    private void initView() {
+
+        // create widgets
+        name = CayenneWidgetFactory.createTextField(25);
+        reverseName = CayenneWidgetFactory.createTextField(25);
+
+        addButton = new JButton("Add");
+        addButton.setEnabled(this.editable);
+
+        removeButton = new JButton("Remove");
+        removeButton.setEnabled(this.editable);
+
+        saveButton = new JButton("Done");
+
+        cancelButton = new JButton("Cancel");
+        cancelButton.setEnabled(this.editable);
+
+        table = new AttributeTable();
+        table.getSelectionModel().setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
+
+        // assemble
+        getContentPane().setLayout(new BorderLayout());
+
+        CellConstraints cc = new CellConstraints();
+        PanelBuilder builder = new PanelBuilder(
+                new FormLayout(
+                        "right:max(50dlu;pref), 3dlu, fill:min(150dlu;pref), 3dlu, fill:min(50dlu;pref)",
+                        "p, 3dlu, p, 3dlu, p, 9dlu, p, 3dlu, top:14dlu, 3dlu, top:p:grow"));
+        builder.setDefaultDialogBorder();
+
+        builder.addSeparator("DbRelationship Information", cc.xywh(1, 1, 5, 1));
+        builder.addLabel("Relationship:", cc.xy(1, 3));
+        builder.add(name, cc.xywh(3, 3, 1, 1));
+        builder.addLabel("Reverse Relationship", cc.xy(1, 5));
+        builder.add(reverseName, cc.xywh(3, 5, 1, 1));
+
+        builder.addSeparator("Joins", cc.xywh(1, 7, 5, 1));
+        builder.add(new JScrollPane(table), cc.xywh(1, 9, 3, 3, "fill, fill"));
+
+        JPanel buttons = new JPanel(new FlowLayout(FlowLayout.LEADING));
+
+        buttons.add(addButton);
+        buttons.add(removeButton);
+
+        builder.add(buttons, cc.xywh(5, 9, 1, 3));
+
+        getContentPane().add(builder.getPanel(), BorderLayout.CENTER);
+        getContentPane().add(PanelFactory.createButtonPanel(new JButton[] {
+                saveButton, cancelButton
+        }), BorderLayout.SOUTH);
+    }
+
+    private void initWithModel(DbRelationship aRelationship) {
+        // sanity check
+        if (aRelationship.getSourceEntity() == null) {
+            throw new CayenneRuntimeException("Null source entity: " + aRelationship);
+        }
+
+        if (aRelationship.getTargetEntity() == null) {
+            throw new CayenneRuntimeException("Null target entity: " + aRelationship);
+        }
+
+        if (aRelationship.getSourceEntity().getDataMap() == null) {
+            throw new CayenneRuntimeException("Null DataMap: "
+                    + aRelationship.getSourceEntity());
+        }
+
+        // Once assigned, can reference relationship directly. Would it be
+        // OK to assign relationship at the very top of this method?
+        relationship = aRelationship;
+        reverseRelationship = relationship.getReverseRelationship();
+
+        // init UI components
+        setTitle("DbRelationship Info: "
+                + relationship.getSourceEntity().getName()
+                + " to "
+                + relationship.getTargetEntityName());
+
+        table.setModel(new DbJoinTableModel(relationship, getMediator(), this, true));
+        TableColumn sourceColumn = table.getColumnModel().getColumn(
+                DbJoinTableModel.SOURCE);
+        sourceColumn.setMinWidth(150);
+        JComboBox comboBox = CayenneWidgetFactory.createComboBox(ModelerUtil
+                .getDbAttributeNames(getMediator(), (DbEntity) relationship
+                        .getSourceEntity()), true);
+
+        AutoCompletion.enable(comboBox);
+        sourceColumn.setCellEditor(CayenneWidgetFactory.createCellEditor(comboBox));
+
+        TableColumn targetColumn = table.getColumnModel().getColumn(
+                DbJoinTableModel.TARGET);
+        targetColumn.setMinWidth(150);
+        comboBox = CayenneWidgetFactory.createComboBox(ModelerUtil.getDbAttributeNames(
+                getMediator(),
+                (DbEntity) relationship.getTargetEntity()), true);
+        AutoCompletion.enable(comboBox);
+
+        targetColumn.setCellEditor(CayenneWidgetFactory.createCellEditor(comboBox));
+
+        if (reverseRelationship != null) {
+            reverseName.setText(reverseRelationship.getName());
+        }
+
+        name.setText(relationship.getName());
+    }
+
+    private void initController() {
+        addButton.addActionListener(new ActionListener() {
+
+            public void actionPerformed(ActionEvent e) {
+                DbJoinTableModel model = (DbJoinTableModel) table.getModel();
+
+                DbJoin join = new DbJoin(relationship);
+                model.addRow(join);
+
+                undo.addDbJoinAddUndo(join);
+
+                table.select(model.getRowCount() - 1);
+            }
+        });
+
+        removeButton.addActionListener(new ActionListener() {
+
+            public void actionPerformed(ActionEvent e) {
+                DbJoinTableModel model = (DbJoinTableModel) table.getModel();
+                stopEditing();
+                int row = table.getSelectedRow();
+
+                DbJoin join = model.getJoin(row);
+                undo.addDbJoinRemoveUndo(join);
+
+                model.removeRow(join);
+            }
+        });
+
+        saveButton.addActionListener(new ActionListener() {
+
+            public void actionPerformed(ActionEvent e) {
+                cancelPressed = false;
+
+                if (editable) {
+                    save();
+                }
+
+                dispose();
+            }
+        });
+
+        cancelButton.addActionListener(new ActionListener() {
+
+            public void actionPerformed(ActionEvent e) {
+                cancelPressed = true;
+                setVisible(false);
+            }
+        });
+    }
+
+    public boolean isCancelPressed() {
+        return cancelPressed;
+    }
+
+    private void stopEditing() {
+        // Stop whatever editing may be taking place
+        int col_index = table.getEditingColumn();
+        if (col_index >= 0) {
+            TableColumn col = table.getColumnModel().getColumn(col_index);
+            col.getCellEditor().stopCellEditing();
+        }
+    }
+
+    private void save() {
+
+        // extract names...
+        String sourceEntityName = name.getText();
+        if (sourceEntityName.length() == 0) {
+            sourceEntityName = null;
+        }
+
+        if (sourceEntityName == null) {
+            sourceEntityName = NamedObjectFactory.createName(
+                    DbRelationship.class,
+                    relationship.getSourceEntity());
+        }
+
+        if (!validateName(relationship.getSourceEntity(), relationship, sourceEntityName)) {
+            return;
+        }
+
+        String targetEntityName = reverseName.getText().trim();
+        if (targetEntityName.length() == 0) {
+            targetEntityName = null;
+        }
+
+        if (targetEntityName == null) {
+            targetEntityName = NamedObjectFactory.createName(
+                    DbRelationship.class,
+                    relationship.getTargetEntity());
+        }
+
+        // check if reverse name is valid
+        DbJoinTableModel model = (DbJoinTableModel) table.getModel();
+        boolean updatingReverse = model.getObjectList().size() > 0;
+
+        if (updatingReverse
+                && !validateName(
+                        relationship.getTargetEntity(),
+                        reverseRelationship,
+                        targetEntityName)) {
+            return;
+        }
+
+        // handle name update
+        if (!Util.nullSafeEquals(sourceEntityName, relationship.getName())) {
+            String oldName = relationship.getName();
+
+            ProjectUtil.setRelationshipName(
+                    relationship.getSourceEntity(),
+                    relationship,
+                    sourceEntityName);
+
+            undo.addNameUndo(relationship, oldName, sourceEntityName);
+
+            getMediator().fireDbRelationshipEvent(
+                    new RelationshipEvent(this, relationship, relationship
+                            .getSourceEntity(), oldName));
+        }
+
+        model.commit();
+
+        // check "to dep pk" setting,
+        // maybe this is no longer valid
+        if (relationship.isToDependentPK() && !relationship.isValidForDepPk()) {
+            relationship.setToDependentPK(false);
+        }
+
+        // If new reverse DbRelationship was created, add it to the target
+        // Don't create reverse with no joins - makes no sense...
+        if (updatingReverse) {
+
+            // If didn't find anything, create reverseDbRel
+            if (reverseRelationship == null) {
+                reverseRelationship = new DbRelationship(targetEntityName);
+                reverseRelationship.setSourceEntity(relationship.getTargetEntity());
+                reverseRelationship.setTargetEntity(relationship.getSourceEntity());
+                reverseRelationship.setToMany(!relationship.isToMany());
+                relationship.getTargetEntity().addRelationship(reverseRelationship);
+
+                // fire only if the relationship is to the same entity...
+                // this is needed to update entity view...
+                if (relationship.getSourceEntity() == relationship.getTargetEntity()) {
+                    getMediator().fireDbRelationshipEvent(
+                            new RelationshipEvent(
+                                    this,
+                                    reverseRelationship,
+                                    reverseRelationship.getSourceEntity(),
+                                    MapEvent.ADD));
+                }
+            }
+            else if (!Util
+                    .nullSafeEquals(targetEntityName, reverseRelationship.getName())) {
+
+                String oldName = reverseRelationship.getName();
+
+                ProjectUtil.setRelationshipName(
+                        reverseRelationship.getSourceEntity(),
+                        reverseRelationship,
+                        targetEntityName);
+
+                undo.addNameUndo(reverseRelationship, oldName, targetEntityName);
+
+                getMediator().fireDbRelationshipEvent(
+                        new RelationshipEvent(
+                                this,
+                                reverseRelationship,
+                                reverseRelationship.getSourceEntity(),
+                                oldName));
+            }
+
+            Collection reverseJoins = getReverseJoins();
+            reverseRelationship.setJoins(reverseJoins);
+
+            // check if joins map to a primary key of this entity
+            if (!relationship.isToDependentPK() && reverseRelationship.isValidForDepPk()) {
+                reverseRelationship.setToDependentPK(true);
+            }
+        }
+
+        Application.getInstance().getUndoManager().addEdit(undo);
+
+        getMediator()
+                .fireDbRelationshipEvent(
+                        new RelationshipEvent(this, relationship, relationship
+                                .getSourceEntity()));
+    }
+
+    private boolean validateName(Entity entity, Relationship aRelationship, String newName) {
+        Relationship existing = entity.getRelationship(newName);
+        if (existing != null && (aRelationship == null || aRelationship != existing)) {
+            JOptionPane.showMessageDialog(
+                    this,
+                    "There is an existing relationship named \""
+                            + newName
+                            + "\". Select a different name.");
+            return false;
+        }
+
+        return true;
+    }
+
+    private Collection getReverseJoins() {
+        Collection<DbJoin> joins = relationship.getJoins();
+
+        if ((joins == null) || (joins.size() == 0)) {
+            return Collections.EMPTY_LIST;
+        }
+
+        List reverseJoins = new ArrayList(joins.size());
+
+        // Loop through the list of attribute pairs, create reverse pairs
+        // and put them to the reverse list.
+        for (DbJoin pair : joins) {
+            DbJoin reverseJoin = pair.createReverseJoin();
+
+            // since reverse relationship is not yet initialized,
+            // reverse join will not have it set automatically
+            reverseJoin.setRelationship(reverseRelationship);
+            reverseJoins.add(reverseJoin);
+        }
+
+        return reverseJoins;
+    }
+
+    final class AttributeTable extends CayenneTable {
+
+        final Dimension preferredSize = new Dimension(203, 100);
+
+        @Override
+        public Dimension getPreferredScrollableViewportSize() {
+            return preferredSize;
+        }
+    }
 }

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/EditorView.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/EditorView.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/EditorView.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/EditorView.java Wed Dec  9 14:12:35 2009
@@ -28,6 +28,7 @@
 import javax.swing.JPanel;
 import javax.swing.JScrollPane;
 import javax.swing.JSplitPane;
+import javax.swing.JTabbedPane;
 
 import org.apache.cayenne.modeler.ProjectController;
 import org.apache.cayenne.modeler.ProjectTreeView;
@@ -90,8 +91,32 @@
     private DbEntityTabbedView dbDetailView;
     private ObjEntityTabbedView objDetailView;
     private EmbeddableTabbedView embeddableView;
+    private DataMapTabbedView dataMapView;
+    private ProcedureTabbedView procedureView;
+    private SelectQueryTabbedView selectQueryView;
+    private SQLTemplateTabbedView sqlTemplateView;
+    private EjbqlTabbedView ejbqlQueryView;
+    private JTabbedPane dataNodeView;
 
     
+    public SelectQueryTabbedView getSelectQueryView() {
+        return selectQueryView;
+    }
+
+    
+    public SQLTemplateTabbedView getSqlTemplateView() {
+        return sqlTemplateView;
+    }
+
+    
+    public EjbqlTabbedView getEjbqlQueryView() {
+        return ejbqlQueryView;
+    }
+
+    public ProcedureTabbedView getProcedureView() {
+        return procedureView;
+    }
+
     public ProjectTreeView getProjectTreeView() {
         return treePanel;
     }
@@ -107,6 +132,14 @@
     public ObjEntityTabbedView getObjDetailView() {
         return objDetailView;
     }
+    
+    public DataMapTabbedView getDataMapView() {
+        return dataMapView;
+    }
+    
+    public JTabbedPane getDataNodeView() {
+        return dataNodeView;
+    }
 
     public EditorView(ProjectController eventController) {
         this.eventController = eventController;

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/EjbqlQueryScriptsTab.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/EjbqlQueryScriptsTab.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/EjbqlQueryScriptsTab.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/EjbqlQueryScriptsTab.java Wed Dec  9 14:12:35 2009
@@ -33,12 +33,14 @@
 import org.apache.cayenne.map.event.QueryEvent;
 import org.apache.cayenne.modeler.ProjectController;
 import org.apache.cayenne.modeler.util.CayenneWidgetFactory;
+import org.apache.cayenne.modeler.util.TextAdapter;
 import org.apache.cayenne.project.validator.EJBQLQueryValidator;
 import org.apache.cayenne.project.validator.EJBQLQueryValidator.PositionException;
 import org.apache.cayenne.query.EJBQLQuery;
 import org.apache.cayenne.query.Query;
 import org.apache.cayenne.swing.components.textpane.JCayenneTextPane;
 import org.apache.cayenne.util.Util;
+import org.apache.cayenne.validation.ValidationException;
 
 public class EjbqlQueryScriptsTab extends JPanel implements DocumentListener {
 
@@ -61,6 +63,13 @@
     private void initView() {
 
         scriptArea = CayenneWidgetFactory.createJEJBQLTextPane();
+        
+        new TextAdapter(scriptArea.getPane()) {
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+        };
+        
         scriptArea.getDocument().addDocumentListener(this);
 
         scriptArea.getDocument().addDocumentListener(new DocumentListener() {

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/SQLTemplateScriptsTab.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/SQLTemplateScriptsTab.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/SQLTemplateScriptsTab.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/SQLTemplateScriptsTab.java Wed Dec  9 14:12:35 2009
@@ -45,9 +45,11 @@
 import org.apache.cayenne.modeler.ProjectController;
 import org.apache.cayenne.modeler.util.CayenneWidgetFactory;
 import org.apache.cayenne.modeler.util.DbAdapterInfo;
+import org.apache.cayenne.modeler.util.TextAdapter;
 import org.apache.cayenne.query.Query;
 import org.apache.cayenne.query.SQLTemplate;
 import org.apache.cayenne.util.Util;
+import org.apache.cayenne.validation.ValidationException;
 import org.syntax.jedit.JEditTextArea;
 import org.syntax.jedit.KeywordMap;
 import org.syntax.jedit.tokenmarker.PLSQLTokenMarker;
@@ -140,6 +142,13 @@
         scripts.setModel(new DefaultComboBoxModel(keys.toArray()));
         
         scriptArea = CayenneWidgetFactory.createJEditTextArea();
+        
+        new TextAdapter(scriptArea) {
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+        };
+        
         scriptArea.setTokenMarker(SQL_TEMPLATE_MARKER);
         scriptArea.getDocument().addDocumentListener(this);
         

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/AdapterView.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/AdapterView.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/AdapterView.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/AdapterView.java Wed Dec  9 14:12:35 2009
@@ -24,17 +24,22 @@
 import javax.swing.JPanel;
 import javax.swing.JTextField;
 
-import org.apache.cayenne.modeler.util.CayenneWidgetFactory;
+import org.apache.cayenne.modeler.util.TextAdapter;
+import org.apache.cayenne.validation.ValidationException;
 
 import com.jgoodies.forms.builder.DefaultFormBuilder;
 import com.jgoodies.forms.layout.FormLayout;
 
 public class AdapterView extends JPanel {
 
-    protected JTextField customAdapter;
+    protected TextAdapter customAdapter;
 
     public AdapterView() {
-        this.customAdapter = CayenneWidgetFactory.createUndoableTextField();
+        this.customAdapter = new TextAdapter(new JTextField()) {
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+        };
 
         // assemble
 
@@ -44,13 +49,13 @@
         topPanelBuilder.setDefaultDialogBorder();
 
         topPanelBuilder.appendSeparator("DbAdapter Configuration");
-        topPanelBuilder.append("Custom Adapter (optional):", customAdapter);
+        topPanelBuilder.append("Custom Adapter (optional):", customAdapter.getComponent());
 
         setLayout(new BorderLayout());
         add(topPanelBuilder.getPanel(), BorderLayout.CENTER);
     }
 
     public JTextField getCustomAdapter() {
-        return customAdapter;
+        return (JTextField) customAdapter.getComponent();
     }
 }

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/CustomDataSourceView.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/CustomDataSourceView.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/CustomDataSourceView.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/CustomDataSourceView.java Wed Dec  9 14:12:35 2009
@@ -24,7 +24,8 @@
 import javax.swing.JPanel;
 import javax.swing.JTextField;
 
-import org.apache.cayenne.modeler.util.CayenneWidgetFactory;
+import org.apache.cayenne.modeler.util.TextAdapter;
+import org.apache.cayenne.validation.ValidationException;
 
 import com.jgoodies.forms.builder.DefaultFormBuilder;
 import com.jgoodies.forms.layout.FormLayout;
@@ -33,11 +34,16 @@
  */
 public class CustomDataSourceView extends JPanel {
 
-    protected JTextField locationHint;
+    protected TextAdapter locationHint;
 
     public CustomDataSourceView() {
 
-        locationHint = CayenneWidgetFactory.createUndoableTextField();
+        locationHint = new TextAdapter(new JTextField()) {
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+            
+        };
 
         // assemble
         FormLayout layout = new FormLayout("right:80dlu, 3dlu, fill:200dlu", "");
@@ -46,13 +52,13 @@
 
         builder.appendSeparator("Custom Configuration");
 
-        builder.append("Location Hint:", locationHint);
+        builder.append("Location Hint:", getLocationHint());
 
         this.setLayout(new BorderLayout());
         this.add(builder.getPanel(), BorderLayout.CENTER);
     }
 
     public JTextField getLocationHint() {
-        return locationHint;
+        return (JTextField) locationHint.getComponent();
     }
 }

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/DBCPDataSourceView.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/DBCPDataSourceView.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/DBCPDataSourceView.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/DBCPDataSourceView.java Wed Dec  9 14:12:35 2009
@@ -17,7 +17,6 @@
  *  under the License.
  ****************************************************************/
 
-
 package org.apache.cayenne.modeler.editor.datanode;
 
 import java.awt.BorderLayout;
@@ -25,7 +24,8 @@
 import javax.swing.JPanel;
 import javax.swing.JTextField;
 
-import org.apache.cayenne.modeler.util.CayenneWidgetFactory;
+import org.apache.cayenne.modeler.util.TextAdapter;
+import org.apache.cayenne.validation.ValidationException;
 
 import com.jgoodies.forms.builder.DefaultFormBuilder;
 import com.jgoodies.forms.layout.FormLayout;
@@ -34,11 +34,16 @@
  */
 public class DBCPDataSourceView extends JPanel {
 
-    protected JTextField propertiesFile;
+    protected TextAdapter propertiesFile;
 
     public DBCPDataSourceView() {
 
-        propertiesFile = CayenneWidgetFactory.createUndoableTextField();
+        propertiesFile = new TextAdapter(new JTextField()) {
+
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+        };
 
         // assemble
         FormLayout layout = new FormLayout("right:80dlu, 3dlu, fill:200dlu", "");
@@ -47,13 +52,13 @@
 
         builder.appendSeparator("Apache DBCP Configuration");
 
-        builder.append("DBCP Properties File:", propertiesFile);
+        builder.append("DBCP Properties File:", getPropertiesFile());
 
         setLayout(new BorderLayout());
         add(builder.getPanel(), BorderLayout.CENTER);
     }
 
     public JTextField getPropertiesFile() {
-        return propertiesFile;
+        return (JTextField) propertiesFile.getComponent();
     }
 }

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/JDBCDataSourceView.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/JDBCDataSourceView.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/JDBCDataSourceView.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/JDBCDataSourceView.java Wed Dec  9 14:12:35 2009
@@ -26,7 +26,8 @@
 import javax.swing.JPasswordField;
 import javax.swing.JTextField;
 
-import org.apache.cayenne.modeler.util.CayenneWidgetFactory;
+import org.apache.cayenne.modeler.util.TextAdapter;
+import org.apache.cayenne.validation.ValidationException;
 
 import com.jgoodies.forms.builder.PanelBuilder;
 import com.jgoodies.forms.layout.CellConstraints;
@@ -34,59 +35,83 @@
 
 public class JDBCDataSourceView extends JPanel {
 
-    protected JTextField     driver;
-    protected JTextField     url;
-    protected JTextField     userName;
+    protected TextAdapter driver;
+    protected TextAdapter url;
+    protected TextAdapter userName;
+
     protected JPasswordField password;
 
-    protected JTextField     minConnections;
-    protected JTextField     maxConnections;
-    protected JButton        syncWithLocal;
+    protected TextAdapter minConnections;
+    protected TextAdapter maxConnections;
 
+    protected JButton syncWithLocal;
 
+    public JDBCDataSourceView() {
 
+        driver = new TextAdapter(new JTextField()) {
 
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+        };
 
+        url = new TextAdapter(new JTextField()) {
 
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+        };
 
-    public JDBCDataSourceView() {
+        userName = new TextAdapter(new JTextField()) {
 
-        driver           = CayenneWidgetFactory.createUndoableTextField();
-        url              = CayenneWidgetFactory.createUndoableTextField();
-        userName         = CayenneWidgetFactory.createUndoableTextField();
-        password         = new JPasswordField();
-        minConnections   = CayenneWidgetFactory.createUndoableTextField(6);
-        maxConnections   = CayenneWidgetFactory.createUndoableTextField(6);
-        syncWithLocal    = new JButton("Sync with Local");
-        syncWithLocal.setToolTipText("Update from local DataSource");
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+        };
+
+        password = new JPasswordField();
+        minConnections = new TextAdapter(new JTextField(6)) {
 
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+        };
 
+        maxConnections = new TextAdapter(new JTextField(6)) {
+
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+        };
+
+        syncWithLocal = new JButton("Sync with Local");
+        syncWithLocal.setToolTipText("Update from local DataSource");
 
         // assemble
         CellConstraints cc = new CellConstraints();
-//        FormLayout layout = new FormLayout(
-//                "right:80dlu, 3dlu, fill:50dlu, 3dlu, fill:74dlu, 3dlu, fill:70dlu",
-//                "p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p");
-        FormLayout layout =
-          new FormLayout("right:80dlu, 3dlu, fill:50dlu, 3dlu, fill:74dlu, 3dlu, fill:70dlu", // Columns
-                         "p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p"); // Rows
+        // FormLayout layout = new FormLayout(
+        // "right:80dlu, 3dlu, fill:50dlu, 3dlu, fill:74dlu, 3dlu, fill:70dlu",
+        // "p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p");
+        FormLayout layout = new FormLayout(
+                "right:80dlu, 3dlu, fill:50dlu, 3dlu, fill:74dlu, 3dlu, fill:70dlu", // Columns
+                "p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p"); // Rows
 
         PanelBuilder builder = new PanelBuilder(layout);
         builder.setDefaultDialogBorder();
-        
+
         builder.addSeparator("JDBC Configuration", cc.xywh(1, 1, 7, 1));
         builder.addLabel("JDBC Driver:", cc.xy(1, 3));
-        builder.add(driver, cc.xywh(3, 3, 5, 1));
+        builder.add(getDriver(), cc.xywh(3, 3, 5, 1));
         builder.addLabel("DB URL:", cc.xy(1, 5));
-        builder.add(url, cc.xywh(3, 5, 5, 1));
+        builder.add(getUrl(), cc.xywh(3, 5, 5, 1));
         builder.addLabel("Username:", cc.xy(1, 7));
-        builder.add(userName, cc.xywh(3, 7, 5, 1));
+        builder.add(getUserName(), cc.xywh(3, 7, 5, 1));
         builder.addLabel("Password:", cc.xy(1, 9));
         builder.add(password, cc.xywh(3, 9, 5, 1));
         builder.addLabel("Min Connections:", cc.xy(1, 11));
-        builder.add(minConnections, cc.xy(3, 11));
+        builder.add(getMinConnections(), cc.xy(3, 11));
         builder.addLabel("Max Connections:", cc.xy(1, 13));
-        builder.add(maxConnections, cc.xy(3, 13));
+        builder.add(getMaxConnections(), cc.xy(3, 13));
         builder.add(syncWithLocal, cc.xy(7, 15));
 
         this.setLayout(new BorderLayout());
@@ -94,7 +119,7 @@
     }
 
     public JTextField getDriver() {
-        return driver;
+        return (JTextField) driver.getComponent();
     }
 
     public JPasswordField getPassword() {
@@ -102,19 +127,19 @@
     }
 
     public JTextField getUrl() {
-        return url;
+        return (JTextField) url.getComponent();
     }
 
     public JTextField getUserName() {
-        return userName;
+        return (JTextField) userName.getComponent();
     }
 
     public JTextField getMaxConnections() {
-        return maxConnections;
+        return (JTextField) maxConnections.getComponent();
     }
 
     public JTextField getMinConnections() {
-        return minConnections;
+        return (JTextField) minConnections.getComponent();
     }
 
     public JButton getSyncWithLocal() {

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/JNDIDataSourceView.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/JNDIDataSourceView.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/JNDIDataSourceView.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/JNDIDataSourceView.java Wed Dec  9 14:12:35 2009
@@ -24,7 +24,8 @@
 import javax.swing.JPanel;
 import javax.swing.JTextField;
 
-import org.apache.cayenne.modeler.util.CayenneWidgetFactory;
+import org.apache.cayenne.modeler.util.TextAdapter;
+import org.apache.cayenne.validation.ValidationException;
 
 import com.jgoodies.forms.builder.DefaultFormBuilder;
 import com.jgoodies.forms.layout.FormLayout;
@@ -33,11 +34,15 @@
  */
 public class JNDIDataSourceView extends JPanel {
 
-    protected JTextField jndiPath;
+    protected TextAdapter jndiPath;
 
     public JNDIDataSourceView() {
 
-        jndiPath = CayenneWidgetFactory.createUndoableTextField();
+        jndiPath = new TextAdapter(new JTextField()) {
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+        };
 
         // assemble
         FormLayout layout = new FormLayout("right:80dlu, 3dlu, fill:200dlu", "");
@@ -46,13 +51,13 @@
 
         builder.appendSeparator("JNDI Configuration");
 
-        builder.append("JNDI Location:", jndiPath);
+        builder.append("JNDI Location:", getJndiPath());
 
         this.setLayout(new BorderLayout());
         this.add(builder.getPanel(), BorderLayout.CENTER);
     }
 
     public JTextField getJndiPath() {
-        return jndiPath;
+        return (JTextField) jndiPath.getComponent();
     }
 }

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/MainDataNodeView.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/MainDataNodeView.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/MainDataNodeView.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/MainDataNodeView.java Wed Dec  9 14:12:35 2009
@@ -30,6 +30,8 @@
 import javax.swing.JTextField;
 
 import org.apache.cayenne.modeler.util.CayenneWidgetFactory;
+import org.apache.cayenne.modeler.util.TextAdapter;
+import org.apache.cayenne.validation.ValidationException;
 
 import com.jgoodies.forms.builder.DefaultFormBuilder;
 import com.jgoodies.forms.layout.FormLayout;
@@ -40,7 +42,8 @@
  */
 public class MainDataNodeView extends JPanel {
 
-    protected JTextField dataNodeName;
+    protected TextAdapter dataNodeName;
+    
     protected JComboBox factories;
     protected JPanel dataSourceDetail;
     protected CardLayout dataSourceDetailLayout;
@@ -51,7 +54,12 @@
     public MainDataNodeView() {
 
         // create widgets
-        this.dataNodeName = CayenneWidgetFactory.createUndoableTextField();
+        this.dataNodeName = new TextAdapter(new JTextField()) {
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+        };
+        
         this.factories = CayenneWidgetFactory.createUndoableComboBox();
         
         this.localDataSources = CayenneWidgetFactory.createUndoableComboBox();
@@ -71,7 +79,7 @@
         topPanelBuilder.setDefaultDialogBorder();
 
         topPanelBuilder.appendSeparator("DataNode Configuration");
-        topPanelBuilder.append("DataNode Name:", dataNodeName, 3);
+        topPanelBuilder.append("DataNode Name:", getDataNodeName(), 3);
         topPanelBuilder.append("Schema Update Strategy:", schemaUpdateStrategy, 3);
 
         DefaultFormBuilder builderForLabel = new DefaultFormBuilder(new FormLayout(
@@ -99,7 +107,7 @@
     }
 
     public JTextField getDataNodeName() {
-        return dataNodeName;
+        return (JTextField) dataNodeName.getComponent();
     }
 
     public JPanel getDataSourceDetail() {

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/PasswordEncoderView.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/PasswordEncoderView.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/PasswordEncoderView.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/editor/datanode/PasswordEncoderView.java Wed Dec  9 14:12:35 2009
@@ -34,148 +34,164 @@
 import org.apache.cayenne.conf.PasswordEncoding;
 import org.apache.cayenne.conn.DataSourceInfo;
 import org.apache.cayenne.modeler.util.CayenneWidgetFactory;
+import org.apache.cayenne.modeler.util.TextAdapter;
+import org.apache.cayenne.validation.ValidationException;
 
 import com.jgoodies.forms.builder.PanelBuilder;
 import com.jgoodies.forms.layout.CellConstraints;
 import com.jgoodies.forms.layout.FormLayout;
 
+public class PasswordEncoderView extends JPanel {
 
-public class PasswordEncoderView extends JPanel{
-    
-    protected JComboBox      passwordEncoder;
-    protected JComboBox      passwordLocation;
-    protected JTextField     passwordKey;
-    protected JTextField     passwordSource;
-    protected JLabel         passwordSourceLabel;
-    
-    private static final String PASSWORD_CLASSPATH  = "Classpath Search (File System)";
+    protected JComboBox passwordEncoder;
+    protected JComboBox passwordLocation;
+
+    protected TextAdapter passwordKey;
+    protected TextAdapter passwordSource;
+
+    protected JLabel passwordSourceLabel;
+
+    private static final String PASSWORD_CLASSPATH = "Classpath Search (File System)";
     private static final String PASSWORD_EXECUTABLE = "Executable Program";
-    private static final String PASSWORD_MODEL      = "Cayenne Model";
-    private static final String PASSWORD_URL        = "URL (file:, http:, etc)";
-    
+    private static final String PASSWORD_MODEL = "Cayenne Model";
+    private static final String PASSWORD_URL = "URL (file:, http:, etc)";
+
     private static final Object[] PASSWORD_LOCATIONS = new Object[] {
-        DataSourceInfo.PASSWORD_LOCATION_MODEL,
-        DataSourceInfo.PASSWORD_LOCATION_CLASSPATH,
-        DataSourceInfo.PASSWORD_LOCATION_EXECUTABLE,
-        DataSourceInfo.PASSWORD_LOCATION_URL };
-    
+            DataSourceInfo.PASSWORD_LOCATION_MODEL,
+            DataSourceInfo.PASSWORD_LOCATION_CLASSPATH,
+            DataSourceInfo.PASSWORD_LOCATION_EXECUTABLE,
+            DataSourceInfo.PASSWORD_LOCATION_URL
+    };
+
     private static final Map<String, String> passwordSourceLabels = new TreeMap<String, String>();
 
-    static
-    {
-      passwordSourceLabels.put(DataSourceInfo.PASSWORD_LOCATION_MODEL, PASSWORD_MODEL);
-      passwordSourceLabels.put(DataSourceInfo.PASSWORD_LOCATION_CLASSPATH, PASSWORD_CLASSPATH);
-      passwordSourceLabels.put(DataSourceInfo.PASSWORD_LOCATION_EXECUTABLE, PASSWORD_EXECUTABLE);
-      passwordSourceLabels.put(DataSourceInfo.PASSWORD_LOCATION_URL, PASSWORD_URL);
-    }
-    
-    final class PasswordLocationRenderer extends DefaultListCellRenderer
-    {
-      public Component getListCellRendererComponent(JList list,
-                                                    Object object,
-                                                    int arg2,
-                                                    boolean arg3,
-                                                    boolean arg4)
-      {
-        if (object != null)
-          object = passwordSourceLabels.get(object);
-        else
-          object = PASSWORD_MODEL;
-
-        return super.getListCellRendererComponent(list, object, arg2, arg3, arg4);
-      }
-    }
-    
-    public PasswordEncoderView(){
-        
-        this.passwordEncoder  = CayenneWidgetFactory.createUndoableComboBox();
+    static {
+        passwordSourceLabels.put(DataSourceInfo.PASSWORD_LOCATION_MODEL, PASSWORD_MODEL);
+        passwordSourceLabels.put(
+                DataSourceInfo.PASSWORD_LOCATION_CLASSPATH,
+                PASSWORD_CLASSPATH);
+        passwordSourceLabels.put(
+                DataSourceInfo.PASSWORD_LOCATION_EXECUTABLE,
+                PASSWORD_EXECUTABLE);
+        passwordSourceLabels.put(DataSourceInfo.PASSWORD_LOCATION_URL, PASSWORD_URL);
+    }
+
+    final class PasswordLocationRenderer extends DefaultListCellRenderer {
+
+        public Component getListCellRendererComponent(
+                JList list,
+                Object object,
+                int arg2,
+                boolean arg3,
+                boolean arg4) {
+            if (object != null)
+                object = passwordSourceLabels.get(object);
+            else
+                object = PASSWORD_MODEL;
+
+            return super.getListCellRendererComponent(list, object, arg2, arg3, arg4);
+        }
+    }
+
+    public PasswordEncoderView() {
+
+        this.passwordEncoder = CayenneWidgetFactory.createUndoableComboBox();
         this.passwordLocation = CayenneWidgetFactory.createUndoableComboBox();
-        this.passwordSource   = CayenneWidgetFactory.createUndoableTextField();
-        this.passwordKey      = CayenneWidgetFactory.createUndoableTextField();
-        
-
-        
-        // init combo box choices                                                                                                                                                                
-        passwordEncoder.setModel(new DefaultComboBoxModel(PasswordEncoding.standardEncoders));
+
+        this.passwordSource = new TextAdapter(new JTextField()) {
+
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+        };
+
+        this.passwordKey = new TextAdapter(new JTextField()) {
+
+            @Override
+            protected void updateModel(String text) throws ValidationException {
+            }
+        };
+
+        // init combo box choices
+        passwordEncoder.setModel(new DefaultComboBoxModel(
+                PasswordEncoding.standardEncoders));
         passwordEncoder.setEditable(true);
 
         passwordLocation = CayenneWidgetFactory.createUndoableComboBox();
         passwordLocation.setRenderer(new PasswordLocationRenderer());
 
-        DefaultComboBoxModel passwordLocationModel = new DefaultComboBoxModel(PASSWORD_LOCATIONS);
+        DefaultComboBoxModel passwordLocationModel = new DefaultComboBoxModel(
+                PASSWORD_LOCATIONS);
 
         passwordLocation.setModel(passwordLocationModel);
 
-        
         CellConstraints cc = new CellConstraints();
 
-        FormLayout layout =
-            new FormLayout("right:80dlu, 3dlu, fill:50dlu, 3dlu, fill:74dlu, 3dlu, fill:70dlu", // Columns
-                   "p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p"); // Rows
-        
+        FormLayout layout = new FormLayout(
+                "right:80dlu, 3dlu, fill:50dlu, 3dlu, fill:74dlu, 3dlu, fill:70dlu", // Columns
+                "p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p, 3dlu, p"); // Rows
+
         PanelBuilder builder = new PanelBuilder(layout);
         builder.setDefaultDialogBorder();
-        
+
         builder.addSeparator("Encoder", cc.xywh(1, 1, 7, 1));
-        
+
         builder.addLabel("Password Encoder:", cc.xy(1, 11));
         builder.add(passwordEncoder, cc.xywh(3, 11, 5, 1));
 
         builder.addLabel("Password Encoder Key:", cc.xy(1, 13));
-        builder.add(passwordKey, cc.xywh(3, 13, 5, 1));
+        builder.add(getPasswordKey(), cc.xywh(3, 13, 5, 1));
 
-        builder.addLabel("Note: Cayenne supplied encoders do not use a key.", cc.xywh(3, 15, 5, 1));
+        builder.addLabel("Note: Cayenne supplied encoders do not use a key.", cc.xywh(
+                3,
+                15,
+                5,
+                1));
 
         builder.addLabel("Password Location:", cc.xy(1, 17));
         builder.add(passwordLocation, cc.xywh(3, 17, 5, 1));
 
         passwordSourceLabel = builder.addLabel("Password Source:", cc.xy(1, 19));
-        builder.add(passwordSource, cc.xywh(3, 19, 5, 1));
-
+        builder.add(getPasswordSource(), cc.xywh(3, 19, 5, 1));
 
         this.setLayout(new BorderLayout());
         this.add(builder.getPanel(), BorderLayout.CENTER);
 
     }
-    
+
     /**
      * @return the passwordEncoder
      */
-    public JComboBox getPasswordEncoder()
-    {
-      return passwordEncoder;
+    public JComboBox getPasswordEncoder() {
+        return passwordEncoder;
     }
 
     /**
      * @return the passwordLocation
      */
-    public JComboBox getPasswordLocation()
-    {
-      return passwordLocation;
+    public JComboBox getPasswordLocation() {
+        return passwordLocation;
     }
 
     /**
      * @return the passwordKey
      */
-    public JTextField getPasswordKey()
-    {
-      return passwordKey;
+    public JTextField getPasswordKey() {
+        return (JTextField) passwordKey.getComponent();
     }
 
     /**
      * @return the passwordSource
      */
-    public JTextField getPasswordSource()
-    {
-      return passwordSource;
+    public JTextField getPasswordSource() {
+        return (JTextField) passwordSource.getComponent();
     }
 
     /**
      * @return the passwordLocationLabel
      */
-    public JLabel getPasswordSourceLabel()
-    {
-      return passwordSourceLabel;
+    public JLabel getPasswordSourceLabel() {
+        return passwordSourceLabel;
     }
 
 }

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/AddPrefetchUndoableEdit.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/AddPrefetchUndoableEdit.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/AddPrefetchUndoableEdit.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/AddPrefetchUndoableEdit.java Wed Dec  9 14:12:35 2009
@@ -26,8 +26,6 @@
 
 public class AddPrefetchUndoableEdit extends AbstractUndoableEdit {
 
-	
-
 	private String prefetch;
 	private SelectQueryPrefetchTab tab;
 

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneTableModelUndoableEdit.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneTableModelUndoableEdit.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneTableModelUndoableEdit.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneTableModelUndoableEdit.java Wed Dec  9 14:12:35 2009
@@ -26,8 +26,6 @@
 
 public class CayenneTableModelUndoableEdit extends AbstractUndoableEdit {
 
-    
-    
     private CayenneTableModel model;
     private Object oldValue;
     private Object newValue;
@@ -36,7 +34,7 @@
 
     @Override
     public String getPresentationName() {
-        return (newValue != null) ? newValue.toString() : "";
+        return "Cell Change";
     }
     
     public CayenneTableModelUndoableEdit(CayenneTableModel model, Object oldValue, Object newValue,

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneUndoManager.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneUndoManager.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneUndoManager.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneUndoManager.java Wed Dec  9 14:12:35 2009
@@ -18,6 +18,8 @@
  ****************************************************************/
 package org.apache.cayenne.modeler.undo;
 
+import javax.swing.event.TreeSelectionEvent;
+import javax.swing.event.TreeSelectionListener;
 import javax.swing.undo.CannotRedoException;
 import javax.swing.undo.CannotUndoException;
 import javax.swing.undo.UndoableEdit;
@@ -26,10 +28,26 @@
 import org.apache.cayenne.modeler.action.RedoAction;
 import org.apache.cayenne.modeler.action.UndoAction;
 import org.apache.cayenne.modeler.util.CayenneAction;
+import org.apache.cayenne.query.EJBQLQuery;
+import org.apache.cayenne.query.SQLTemplate;
 
-public class CayenneUndoManager extends javax.swing.undo.UndoManager {
+public class CayenneUndoManager extends javax.swing.undo.UndoManager implements
+        TreeSelectionListener {
 
-    
+    public void valueChanged(TreeSelectionEvent event) {
+
+        UndoableEdit e = editToBeUndone();
+
+        if (e instanceof TextCompoundEdit) {
+            TextCompoundEdit edit = (TextCompoundEdit) e;
+
+            if (edit.getTargetObject() instanceof SQLTemplate
+                    || edit.getTargetObject() instanceof EJBQLQuery) {
+                trimEdits(edits.size() - 1, edits.size() - 1);
+                updateUI();
+            }
+        }
+    }
 
     private Application application;
 
@@ -37,14 +55,13 @@
         this.application = application;
         setLimit(100);
     }
-    
-    
+
     @Override
     public synchronized void discardAllEdits() {
         super.discardAllEdits();
         updateUI();
     }
-    
+
     @Override
     public synchronized boolean addEdit(UndoableEdit anEdit) {
         boolean result = super.addEdit(anEdit);
@@ -54,21 +71,48 @@
 
     @Override
     public synchronized void redo() throws CannotRedoException {
-        super.redo();
+        UndoableEdit e = editToBeRedone();
+
+        if (e instanceof TextCompoundEdit) {
+            TextCompoundEdit edit = (TextCompoundEdit) e;
+
+            edit.watchCaretPosition();
+
+            super.redo();
+
+            edit.stopWatchingCaretPosition();
+        }
+        else {
+            super.redo();
+        }
+
         updateUI();
     }
 
-
     @Override
     public synchronized void undo() throws CannotUndoException {
-        super.undo();
+        UndoableEdit e = editToBeUndone();
+
+        if (e instanceof TextCompoundEdit) {
+            TextCompoundEdit edit = (TextCompoundEdit) e;
+
+            edit.watchCaretPosition();
+
+            super.undo();
+
+            edit.stopWatchingCaretPosition();
+        }
+        else {
+            super.undo();
+        }
+
         updateUI();
     }
 
     private void updateUI() {
         CayenneAction undoAction = application.getActionManager().getAction(
                 UndoAction.getActionName());
-        
+
         CayenneAction redoAction = application.getActionManager().getAction(
                 RedoAction.getActionName());
 

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneUndoableEdit.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneUndoableEdit.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneUndoableEdit.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CayenneUndoableEdit.java Wed Dec  9 14:12:35 2009
@@ -18,39 +18,29 @@
  ****************************************************************/
 package org.apache.cayenne.modeler.undo;
 
-import javax.swing.tree.TreePath;
 import javax.swing.undo.AbstractUndoableEdit;
 
 import org.apache.cayenne.modeler.ActionManager;
 import org.apache.cayenne.modeler.Application;
-import org.apache.cayenne.modeler.CayenneModelerFrame;
 import org.apache.cayenne.modeler.ProjectController;
-import org.apache.cayenne.modeler.ProjectTreeView;
 
 public abstract class CayenneUndoableEdit extends AbstractUndoableEdit {
-	
-
-	protected ProjectTreeView treeView;
+    
 	protected ActionManager actionManager;
 	protected ProjectController controller;
 	
-	private TreePath[] paths;
-	
-
 	public CayenneUndoableEdit() {
-		this.treeView = ((CayenneModelerFrame) Application.getInstance()
-				.getFrameController().getView()).getView().getProjectTreeView();
 		this.actionManager = Application.getInstance().getActionManager();
-		this.paths = this.treeView.getSelectionPaths();
 		this.controller = Application.getInstance().getFrameController().getProjectController();
 	}
 
-	protected void restoreSelections() {
-		this.treeView.setSelectionPaths(paths);
-	}
-
 	@Override
 	public boolean canRedo() {
 		return true;
 	}
+
+    @Override
+    public boolean canUndo() {
+        return true;
+    }
 }

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CreateAttributeUndoableEdit.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CreateAttributeUndoableEdit.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CreateAttributeUndoableEdit.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CreateAttributeUndoableEdit.java Wed Dec  9 14:12:35 2009
@@ -39,7 +39,6 @@
 	}
 
 	
-
 	@Override
 	public String getPresentationName() {
 		return "Create Attribute";
@@ -55,9 +54,7 @@
 	private DbAttribute dbAttr;
 
 	@Override
-	public void redo() throws CannotRedoException {
-		restoreSelections();
-		
+	public void redo() throws CannotRedoException {		
 		CreateAttributeAction action = (CreateAttributeAction) actionManager
 				.getAction(CreateAttributeAction.getActionName());
 
@@ -71,9 +68,7 @@
 	}
 
 	@Override
-	public void undo() throws CannotUndoException {
-		restoreSelections();
-		
+	public void undo() throws CannotUndoException {		
 		RemoveAttributeAction action = (RemoveAttributeAction) actionManager
 				.getAction(RemoveAttributeAction.getActionName());
 
@@ -115,5 +110,4 @@
 		this.dbEntity = dbEntity;
 		this.dbAttr = attr;
 	}
-
 }

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CreateRelationshipUndoableEdit.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CreateRelationshipUndoableEdit.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CreateRelationshipUndoableEdit.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/CreateRelationshipUndoableEdit.java Wed Dec  9 14:12:35 2009
@@ -31,13 +31,6 @@
 
 public class CreateRelationshipUndoableEdit extends CayenneUndoableEdit {
 
-    @Override
-    public String getPresentationName() {
-        return "Create Relationship";
-    }
-
-    
-
     private ObjEntity objEnt;
     private ObjRelationship[] objectRel;
 
@@ -53,6 +46,11 @@
         this.dbEnt = dbEnt;
         this.dbRel = dbRel;
     }
+    
+    @Override
+    public String getPresentationName() {
+        return "Create Relationship";
+    }
 
     @Override
     public void redo() throws CannotRedoException {

Added: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/DbEntitySyncUndoableEdit.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/DbEntitySyncUndoableEdit.java?rev=888809&view=auto
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/DbEntitySyncUndoableEdit.java (added)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/DbEntitySyncUndoableEdit.java Wed Dec  9 14:12:35 2009
@@ -0,0 +1,111 @@
+/*****************************************************************
+ *   Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ ****************************************************************/
+package org.apache.cayenne.modeler.undo;
+
+import java.util.Collection;
+
+import javax.swing.undo.CompoundEdit;
+
+import org.apache.cayenne.access.DataDomain;
+import org.apache.cayenne.map.DataMap;
+import org.apache.cayenne.map.DbAttribute;
+import org.apache.cayenne.map.ObjAttribute;
+import org.apache.cayenne.map.ObjEntity;
+import org.apache.cayenne.map.ObjRelationship;
+import org.apache.cayenne.util.EntityMergeListener;
+
+public class DbEntitySyncUndoableEdit extends CompoundEdit {
+
+    @Override
+    public boolean isInProgress() {
+        return false;
+    }
+
+    @Override
+    public boolean canUndo() {
+        return !edits.isEmpty();
+    }
+
+    private DataDomain domain;
+    private DataMap map;
+
+    public DbEntitySyncUndoableEdit(DataDomain domain, DataMap map) {
+        super();
+        this.domain = domain;
+        this.map = map;
+    }
+
+    public class EntitySyncUndoableListener implements EntityMergeListener {
+
+        private ObjEntity entity;
+
+        public EntitySyncUndoableListener(ObjEntity entity) {
+            this.entity = entity;
+        }
+
+        public void objRelationshipAdded(ObjRelationship rel) {
+            addEdit(new CreateRelationshipUndoableEdit(entity, new ObjRelationship[] {
+                rel
+            }));
+        }
+
+        public void objAttributeAdded(ObjAttribute attr) {
+            addEdit(new CreateAttributeUndoableEdit(domain, map, entity, attr));
+        }
+    }
+
+    public class MeaningfulFKsUndoableEdit extends CompoundEdit {
+
+        @Override
+        public boolean isInProgress() {
+            return false;
+        }
+
+        @Override
+        public boolean canUndo() {
+            return !edits.isEmpty();
+        }
+
+        public MeaningfulFKsUndoableEdit(ObjEntity entity, Collection<DbAttribute> dbAttrs) {
+            for (DbAttribute da : dbAttrs) {
+                ObjAttribute oa = entity.getAttributeForDbAttribute(da);
+                while (oa != null) {
+                    addEdit(new RemoveAttributeUndoableEdit(
+                            domain,
+                            map,
+                            entity,
+                            new ObjAttribute[] {
+                                oa
+                            }));
+                    oa = entity.getAttributeForDbAttribute(da);
+                }
+            }
+        }
+    }
+
+    @Override
+    public String getRedoPresentationName() {
+        return "Redo Db Entity Sync";
+    }
+
+    @Override
+    public String getUndoPresentationName() {
+        return "Undo Db Entity Sync";
+    }
+}

Modified: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/InferRelationshipsUndoableEdit.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/InferRelationshipsUndoableEdit.java?rev=888809&r1=888808&r2=888809&view=diff
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/InferRelationshipsUndoableEdit.java (original)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/InferRelationshipsUndoableEdit.java Wed Dec  9 14:12:35 2009
@@ -18,9 +18,10 @@
  ****************************************************************/
 package org.apache.cayenne.modeler.undo;
 
+import javax.swing.undo.CompoundEdit;
 
-public class InferRelationshipsUndoableEdit extends CayenneCompoundEdit {
-    
+
+public class InferRelationshipsUndoableEdit extends CompoundEdit {
  
     @Override
     public String getPresentationName() {

Added: cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/JEditTextAreaUndoableAdapter.java
URL: http://svn.apache.org/viewvc/cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/JEditTextAreaUndoableAdapter.java?rev=888809&view=auto
==============================================================================
--- cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/JEditTextAreaUndoableAdapter.java (added)
+++ cayenne/main/branches/STABLE-3.0/framework/cayenne-modeler/src/main/java/org/apache/cayenne/modeler/undo/JEditTextAreaUndoableAdapter.java Wed Dec  9 14:12:35 2009
@@ -0,0 +1,96 @@
+/*****************************************************************
+ *   Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ ****************************************************************/
+package org.apache.cayenne.modeler.undo;
+
+import java.awt.event.FocusListener;
+
+import javax.swing.JTextField;
+import javax.swing.text.Document;
+
+import org.syntax.jedit.JEditTextArea;
+
+public class JEditTextAreaUndoableAdapter extends JTextField {
+
+    @Override
+    public synchronized void addFocusListener(FocusListener l) {
+        if (textArea != null) {
+            textArea.addFocusListener(l);
+        }
+    }
+
+    private JEditTextArea textArea;
+
+    public JEditTextAreaUndoableAdapter(JEditTextArea scriptArea) {
+        this.textArea = scriptArea;
+    }
+
+    public int getCaretPosition() {
+        if (textArea == null) {
+            return 0;
+        }
+
+        return textArea.getCaretPosition();
+    }
+
+    public Document getDocument() {
+        if (textArea == null) {
+            return null;
+        }
+
+        return textArea.getDocument();
+    }
+
+    public boolean requestFocusInWindow() {
+        if (textArea == null) {
+            return false;
+        }
+
+        return textArea.requestFocusInWindow();
+    }
+
+    public void selectAll() {
+        if (textArea == null) {
+            return;
+        }
+
+        textArea.selectAll();
+    }
+
+    @Override
+    public void setText(String t) {
+        if (textArea == null) {
+            return;
+        }
+
+        textArea.setText(t);
+    }
+
+    public void setCaretPosition(int position) {
+        if (textArea == null) {
+            return;
+        }
+
+        textArea.setCaretPosition(position);
+    }
+
+    @Override
+    public void updateUI() {
+
+    }
+}