001: /* Copyright (C) 2003 Finalist IT Group
002: *
003: * This file is part of JAG - the Java J2EE Application Generator
004: *
005: * JAG is free software; you can redistribute it and/or modify
006: * it under the terms of the GNU General Public License as published by
007: * the Free Software Foundation; either version 2 of the License, or
008: * (at your option) any later version.
009: * JAG is distributed in the hope that it will be useful,
010: * but WITHOUT ANY WARRANTY; without even the implied warranty of
011: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
012: * GNU General Public License for more details.
013: * You should have received a copy of the GNU General Public License
014: * along with JAG; if not, write to the Free Software
015: * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
016: */
017:
018: package com.finalist.jaggenerator.modules;
019:
020: import com.finalist.jaggenerator.*;
021: import com.finalist.jag.util.TemplateString;
022:
023: import javax.swing.*;
024: import java.util.Iterator;
025: import java.util.List;
026: import java.util.ArrayList;
027:
028: /**
029: *
030: * @author m.oconnor, r. ekkelenkamp
031: */
032: public class RelationPanel extends javax.swing.JPanel {
033: private static final String ONE_TO_ONE = "one to one";
034: private static final String ONE_TO_MANY = "one to many";
035: private static final String MANY_TO_ONE = "many to one";
036: private Relation model;
037: private boolean constructed = false;
038:
039: /**
040: * Creates new form RelationPanel
041: *
042: * @param relation The Relation that this object views.
043: * @param waitForInitSignal if <code>true</code> delay initialisation until notified.
044: */
045: public RelationPanel(Relation relation,
046: final boolean waitForInitSignal) {
047: model = relation;
048: initComponents();
049: if (waitForInitSignal) {
050: new Thread("RelationPanel(" + model.getName() + ")") {
051: public void run() {
052: initValues(true);
053: }
054: }.start();
055: } else {
056: initValues(false);
057: }
058: }
059:
060: public void initValues(boolean waitForInitSignal) {
061: constructed = false;
062: final boolean initFromXML = !JagGenerator.isDatabaseConnected();
063: nameField.setText(model.getName());
064:
065: //init list of selected tables (excluding local table)
066: foreignTableCombo.removeAllItems();
067: List tableList = null;
068: if (initFromXML) {
069: tableList = new ArrayList();
070: tableList.add(model.getForeignTable());
071: foreignTableCombo.setEditable(true);
072: } else {
073: foreignTableCombo.setEditable(false);
074: tableList = DatabaseUtils.getTables();
075: }
076:
077: Iterator tables = tableList.iterator();
078: while (tables.hasNext()) {
079: String tableName = (String) tables.next();
080: TemplateString localTableName = model.getLocalEntity()
081: .getLocalTableName();
082: if (tableName != null && localTableName != null
083: && !tableName.equals(localTableName.toString())) {
084: foreignTableCombo.addItem(tableName);
085: }
086: }
087: foreignTableCombo.setSelectedItem(model.getForeignTable());
088:
089: initColumnsList();
090:
091: //cardinalityCombo.addItem(ONE_TO_ONE);
092: cardinalityCombo.addItem(MANY_TO_ONE);
093: cardinalityCombo.setSelectedItem(MANY_TO_ONE);
094: /*
095: * Currently only Many to one is supported.
096: if (model.isTargetMultiple()) {
097: cardinalityCombo.setSelectedItem(MANY_TO_ONE);
098: } else {
099: cardinalityCombo.setSelectedItem(ONE_TO_ONE);
100: }
101: */
102: if (model.isBidirectional()) {
103: bidirectionalCheckbox.setSelected(true);
104: } else {
105: bidirectionalCheckbox.setSelected(false);
106: }
107:
108: if (waitForInitSignal) {
109: synchronized (this ) {
110: try {
111: //wait for the local-side entity to finish being constructed before finishing off..
112: wait();
113: updateFieldsCombo();
114:
115: } catch (InterruptedException e) {
116: e.printStackTrace();
117: }
118: }
119: } else {
120: updateFieldsCombo();
121: }
122:
123: //initially the field referred to by this relation might not be aware it's a foreign key - make it so..
124: Iterator parentFields = model.getLocalEntity().getFields()
125: .iterator();
126: while (parentFields.hasNext()) {
127: Field field = (Field) parentFields.next();
128: if (field.getName().toString().equals(
129: fkFieldCombo.getSelectedItem())) {
130: field.setForeignKey(true);
131: }
132: }
133:
134: constructed = true;
135: }
136:
137: /**
138: * Sometimes it is necessary to force an update of the relation name in the view
139: * from the model. This method does that!
140: * @param relationName the new name.
141: */
142: public void setName(String relationName) {
143: nameField.setText(relationName);
144: }
145:
146: public void updateFieldName(String oldName, String newName) {
147: Object selected = fkFieldCombo.getSelectedItem();
148: ArrayList contents = new ArrayList();
149: for (int i = 0; i < fkFieldCombo.getModel().getSize(); i++) {
150: Object field = fkFieldCombo.getModel().getElementAt(i);
151: if (field.equals(oldName)) {
152: contents.add(newName);
153: if (selected.equals(field)) {
154: selected = newName;
155: }
156: } else {
157: contents.add(field);
158: }
159: }
160:
161: fkFieldCombo.removeAllItems();
162: Iterator newList = contents.iterator();
163: while (newList.hasNext()) {
164: Object o = newList.next();
165: fkFieldCombo.addItem(o);
166: }
167: fkFieldCombo.setSelectedItem(selected);
168: }
169:
170: private void updateFieldsCombo() {
171: //init list of fields from local entity bean
172: fkFieldCombo.removeAllItems();
173: Iterator fields = model.getLocalEntity().getFields().iterator();
174: while (fields.hasNext()) {
175: Field field = (Field) fields.next();
176: fkFieldCombo.addItem(field.getName().toString());
177: if (field.getName().equals(model.getFieldName())) {
178: fkFieldCombo
179: .setSelectedItem(field.getName().toString());
180: }
181: }
182: }
183:
184: private void initColumnsList() {
185: foreignPkCombo.removeAllItems();
186: String selectedTable = (String) foreignTableCombo
187: .getSelectedItem();
188: List columnsList = null;
189: if (JagGenerator.isDatabaseConnected()) {
190: columnsList = DatabaseUtils.getColumns(selectedTable);
191: }
192: if (columnsList == null || columnsList.isEmpty()) {
193: foreignPkCombo.addItem(model.getForeignColumn());
194: foreignPkCombo.setEditable(true);
195: } else {
196: foreignPkCombo.setEditable(false);
197: Iterator columns = columnsList.iterator();
198: while (columns.hasNext()) {
199: Column column = (Column) columns.next();
200: foreignPkCombo.addItem(column.getName());
201: if (column.isPrimaryKey()) {
202: foreignPkCombo.setSelectedItem(column.getName());
203: }
204: }
205: }
206: }
207:
208: private void formPropertyChange() {
209: if (constructed) {
210: model.setName(nameField.getText());
211: String oldFkField = model.getFieldName().toString();
212: String newFkField = getTextFromJComboBox(fkFieldCombo);
213: model.setFieldName(newFkField);
214: if (oldFkField != null && !oldFkField.equals(newFkField)) {
215: JagGenerator.setForeignKeyInField(model
216: .getLocalEntity().getLocalTableName()
217: .toString(), newFkField);
218: }
219: model
220: .setForeignTable(getTextFromJComboBox(foreignTableCombo));
221: model
222: .setForeignColumn(getTextFromJComboBox(foreignPkCombo));
223: model.setForeignPkFieldName(Utils
224: .format(getTextFromJComboBox(foreignPkCombo)));
225: model.setTargetMultiple(MANY_TO_ONE
226: .equals(getTextFromJComboBox(cardinalityCombo)));
227: model.setBidirectional(bidirectionalCheckbox
228: .getSelectedObjects() != null);
229: }
230: JagGenerator.stateChanged(false);
231: }
232:
233: /** This method is called from within the constructor to
234: * initialize the form.
235: * WARNING: Do NOT modify this code. The content of this method is
236: * always regenerated by the Form Editor.
237: */
238: private void initComponents() {//GEN-BEGIN:initComponents
239: jLabel1 = new javax.swing.JLabel();
240: nameField = new javax.swing.JTextField();
241: nameLabel = new javax.swing.JLabel();
242: fkFieldLabel = new javax.swing.JLabel();
243: foreignTableCombo = new javax.swing.JComboBox();
244: foreignTableLabel = new javax.swing.JLabel();
245: fkFieldCombo = new javax.swing.JComboBox();
246: foreignPkLabel = new javax.swing.JLabel();
247: foreignPkCombo = new javax.swing.JComboBox();
248: bidirectionalCheckbox = new javax.swing.JCheckBox();
249: cardinalityLabel = new javax.swing.JLabel();
250: cardinalityCombo = new javax.swing.JComboBox();
251:
252: setLayout(null);
253:
254: addMouseListener(new java.awt.event.MouseAdapter() {
255: public void mouseExited(java.awt.event.MouseEvent evt) {
256: formMouseExited(evt);
257: }
258: });
259:
260: jLabel1.setFont(new java.awt.Font("Arial", 0, 12));
261: jLabel1
262: .setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
263: jLabel1.setText("- relation -");
264: add(jLabel1);
265: jLabel1.setBounds(110, 20, 380, 15);
266:
267: nameField.addFocusListener(new java.awt.event.FocusAdapter() {
268: public void focusLost(java.awt.event.FocusEvent evt) {
269: nameFieldFocusLost(evt);
270: }
271: });
272:
273: add(nameField);
274: nameField.setBounds(190, 70, 260, 20);
275:
276: nameLabel.setFont(new java.awt.Font("Dialog", 0, 12));
277: nameLabel.setText("relation name:");
278: nameLabel
279: .setToolTipText("The name used internally to represent this (end of the) relation.");
280: add(nameLabel);
281: nameLabel.setBounds(20, 70, 120, 20);
282:
283: fkFieldLabel.setFont(new java.awt.Font("Dialog", 0, 12));
284: fkFieldLabel.setText("foreign key field:");
285: add(fkFieldLabel);
286: fkFieldLabel.setBounds(20, 100, 120, 20);
287:
288: foreignTableCombo
289: .addActionListener(new java.awt.event.ActionListener() {
290: public void actionPerformed(
291: java.awt.event.ActionEvent evt) {
292: foreignTableComboActionPerformed(evt);
293: }
294: });
295: foreignTableCombo
296: .addFocusListener(new java.awt.event.FocusAdapter() {
297: public void focusLost(java.awt.event.FocusEvent evt) {
298: foreignTableComboFocusLost(evt);
299: }
300: });
301:
302: add(foreignTableCombo);
303: foreignTableCombo.setBounds(190, 160, 260, 23);
304:
305: foreignTableLabel.setFont(new java.awt.Font("Dialog", 0, 12));
306: foreignTableLabel.setText("foreign table:");
307: add(foreignTableLabel);
308: foreignTableLabel.setBounds(20, 160, 120, 20);
309:
310: fkFieldCombo
311: .addActionListener(new java.awt.event.ActionListener() {
312: public void actionPerformed(
313: java.awt.event.ActionEvent evt) {
314: fkFieldComboActionPerformed(evt);
315: }
316: });
317:
318: add(fkFieldCombo);
319: fkFieldCombo.setBounds(190, 100, 260, 23);
320:
321: foreignPkLabel.setFont(new java.awt.Font("Dialog", 0, 12));
322: foreignPkLabel.setText("foreign table's primary key:");
323: add(foreignPkLabel);
324: foreignPkLabel.setBounds(20, 190, 160, 20);
325:
326: foreignPkCombo
327: .addActionListener(new java.awt.event.ActionListener() {
328: public void actionPerformed(
329: java.awt.event.ActionEvent evt) {
330: foreignPkComboActionPerformed(evt);
331: }
332: });
333: foreignPkCombo
334: .addFocusListener(new java.awt.event.FocusAdapter() {
335: public void focusLost(java.awt.event.FocusEvent evt) {
336: foreignPkComboFocusLost(evt);
337: }
338: });
339:
340: add(foreignPkCombo);
341: foreignPkCombo.setBounds(190, 190, 260, 23);
342:
343: bidirectionalCheckbox
344: .setFont(new java.awt.Font("Dialog", 0, 12));
345: bidirectionalCheckbox.setText("bi-directional relationship?");
346: add(bidirectionalCheckbox);
347: bidirectionalCheckbox.setBounds(20, 280, 190, 25);
348:
349: cardinalityLabel.setFont(new java.awt.Font("Dialog", 0, 12));
350: cardinalityLabel.setText("cardinality:");
351: add(cardinalityLabel);
352: cardinalityLabel.setBounds(20, 250, 160, 20);
353:
354: cardinalityCombo
355: .addActionListener(new java.awt.event.ActionListener() {
356: public void actionPerformed(
357: java.awt.event.ActionEvent evt) {
358: cardinalityComboActionPerformed(evt);
359: }
360: });
361:
362: add(cardinalityCombo);
363: cardinalityCombo.setBounds(190, 250, 260, 23);
364:
365: }//GEN-END:initComponents
366:
367: private void cardinalityComboActionPerformed(
368: java.awt.event.ActionEvent evt) {//GEN-FIRST:event_cardinalityComboActionPerformed
369: // TODO add your handling code here:
370: }//GEN-LAST:event_cardinalityComboActionPerformed
371:
372: private void foreignPkComboFocusLost(java.awt.event.FocusEvent evt) {//GEN-FIRST:event_foreignPkComboFocusLost
373: formPropertyChange();
374: JagGenerator.stateChanged(false);
375: }//GEN-LAST:event_foreignPkComboFocusLost
376:
377: private void foreignTableComboFocusLost(
378: java.awt.event.FocusEvent evt) {//GEN-FIRST:event_foreignTableComboFocusLost
379: formPropertyChange();
380: JagGenerator.stateChanged(false);
381: }//GEN-LAST:event_foreignTableComboFocusLost
382:
383: private void fkFieldComboActionPerformed(
384: java.awt.event.ActionEvent evt) {//GEN-FIRST:event_fkFieldComboActionPerformed
385: formPropertyChange();
386: }//GEN-LAST:event_fkFieldComboActionPerformed
387:
388: private void formMouseExited(java.awt.event.MouseEvent evt) {//GEN-FIRST:event_formMouseExited
389: //this is necessary to make sure the field currenlty having focus
390: //is synched with the panel when the File > Save menu is selected.
391: formPropertyChange();
392: }//GEN-LAST:event_formMouseExited
393:
394: private void foreignPkComboActionPerformed(
395: java.awt.event.ActionEvent evt) {//GEN-FIRST:event_foreignPkComboActionPerformed
396: formPropertyChange();
397: }//GEN-LAST:event_foreignPkComboActionPerformed
398:
399: private void nameFieldFocusLost(java.awt.event.FocusEvent evt) {//GEN-FIRST:event_nameFieldFocusLost
400: formPropertyChange();
401: JagGenerator.stateChanged(true);
402: }//GEN-LAST:event_nameFieldFocusLost
403:
404: private void foreignTableComboActionPerformed(
405: java.awt.event.ActionEvent evt) {//GEN-FIRST:event_foreignTableComboActionPerformed
406: evt = null;
407: formPropertyChange();
408: initColumnsList();
409: JagGenerator.stateChanged(false);
410: }//GEN-LAST:event_foreignTableComboActionPerformed
411:
412: private String getTextFromJComboBox(JComboBox combo) {
413: String a = (String) combo.getEditor().getItem();
414: String b = (String) combo.getSelectedItem();
415: return combo.isEditable() ? a : b;
416: }
417:
418: // Variables declaration - do not modify//GEN-BEGIN:variables
419: private javax.swing.JCheckBox bidirectionalCheckbox;
420: private javax.swing.JComboBox cardinalityCombo;
421: private javax.swing.JLabel cardinalityLabel;
422: private javax.swing.JComboBox fkFieldCombo;
423: private javax.swing.JLabel fkFieldLabel;
424: private javax.swing.JComboBox foreignPkCombo;
425: private javax.swing.JLabel foreignPkLabel;
426: private javax.swing.JComboBox foreignTableCombo;
427: private javax.swing.JLabel foreignTableLabel;
428: private javax.swing.JLabel jLabel1;
429: private javax.swing.JTextField nameField;
430: private javax.swing.JLabel nameLabel;
431: // End of variables declaration//GEN-END:variables
432:
433: }
|