001: package net.sourceforge.squirrel_sql.client.gui.db;
002:
003: /*
004: * Copyright (C) 2001-2004 Colin Bell and Johan Compagner
005: * colbell@users.sourceforge.net
006: * jcompagner@j-com.nl
007: *
008: * This library is free software; you can redistribute it and/or
009: * modify it under the terms of the GNU Lesser General Public
010: * License as published by the Free Software Foundation; either
011: * version 2.1 of the License, or (at your option) any later version.
012: *
013: * This library is distributed in the hope that it will be useful,
014: * but WITHOUT ANY WARRANTY; without even the implied warranty of
015: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
016: * Lesser General Public License for more details.
017: *
018: * You should have received a copy of the GNU Lesser General Public
019: * License along with this library; if not, write to the Free Software
020: * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
021: */
022: import com.jgoodies.forms.builder.PanelBuilder;
023: import com.jgoodies.forms.layout.CellConstraints;
024: import com.jgoodies.forms.layout.FormLayout;
025: import net.sourceforge.squirrel_sql.client.IApplication;
026: import net.sourceforge.squirrel_sql.client.resources.SquirrelResources;
027: import net.sourceforge.squirrel_sql.client.gui.BaseInternalFrame;
028: import net.sourceforge.squirrel_sql.client.gui.IOkClosePanelListener;
029: import net.sourceforge.squirrel_sql.client.gui.OkClosePanel;
030: import net.sourceforge.squirrel_sql.client.gui.OkClosePanelEvent;
031: import net.sourceforge.squirrel_sql.client.mainframe.action.AliasPropertiesCommand;
032: import net.sourceforge.squirrel_sql.fw.gui.GUIUtils;
033: import net.sourceforge.squirrel_sql.fw.gui.StatusBar;
034: import net.sourceforge.squirrel_sql.fw.sql.ISQLAlias;
035: import net.sourceforge.squirrel_sql.fw.sql.ISQLDriver;
036: import net.sourceforge.squirrel_sql.fw.sql.SQLDriverPropertyCollection;
037: import net.sourceforge.squirrel_sql.fw.util.StringManager;
038: import net.sourceforge.squirrel_sql.fw.util.StringManagerFactory;
039: import net.sourceforge.squirrel_sql.fw.util.log.ILogger;
040: import net.sourceforge.squirrel_sql.fw.util.log.LoggerController;
041:
042: import javax.swing.*;
043: import javax.swing.event.InternalFrameAdapter;
044: import javax.swing.event.InternalFrameEvent;
045: import java.awt.*;
046: import java.awt.event.ActionEvent;
047: import java.awt.event.ActionListener;
048: import java.awt.event.KeyEvent;
049:
050: /**
051: * This internal frame allows the user to connect to an alias.
052: *
053: * @author <A HREF="mailto:colbell@users.sourceforge.net">Colin Bell</A>
054: */
055: public class ConnectionInternalFrame extends BaseInternalFrame {
056: /** Handler called for internal frame actions. */
057: public interface IHandler {
058: /**
059: * User has clicked the OK button to connect to the alias.
060: *
061: * @param connSheet The connection internal frame.
062: * @param user The user name entered.
063: * @param password The password entered.
064: * @param props SQLDriverPropertyCollection to connect with.
065: */
066: public void performOK(ConnectionInternalFrame connSheet,
067: String user, String password,
068: SQLDriverPropertyCollection props);
069:
070: /**
071: * User has clicked the Close button. They don't want to
072: * connect to the alias.
073: *
074: * @param connSheet The connection internal frame.
075: */
076: public void performClose(ConnectionInternalFrame connSheet);
077:
078: /**
079: * User has clicked the Cancel button. They want to cancel
080: * the curently active attempt to connect to the database.
081: *
082: * @param connSheet The connection internal frame.
083: */
084: public void performCancelConnect(
085: ConnectionInternalFrame connSheet);
086: }
087:
088: /** Internationalized strings for this class. */
089: private static final StringManager s_stringMgr = StringManagerFactory
090: .getStringManager(ConnectionInternalFrame.class);
091:
092: /** Logger for this class. */
093: private static final ILogger s_log = LoggerController
094: .createLogger(ConnectionInternalFrame.class);
095:
096: /** Application API. */
097: private IApplication _app;
098:
099: /** Alias we are going to connect to. */
100: private ISQLAlias _alias;
101:
102: /** JDBC driver for <TT>_alias</TT>. */
103: private ISQLDriver _sqlDriver;
104:
105: /** <TT>true</TT> means that an attempt is being made to connect to the alias.*/
106: private boolean _connecting;
107:
108: // private SQLDriverPropertyCollection _props = new SQLDriverPropertyCollection();
109:
110: private IHandler _handler;
111:
112: private JLabel _aliasName = new JLabel();
113: private JLabel _driverName = new JLabel();
114: private JLabel _url = new JLabel();
115: private JTextField _user = new JTextField();
116: private JTextField _password = new JPasswordField();
117: private OkClosePanel _btnsPnl = new OkClosePanel(s_stringMgr
118: .getString("ConnectionInternalFrame.connect"));
119:
120: private boolean _driverPropertiesLoaded = false;
121:
122: // /** If checked use the extended driver properties. */
123: // private final JCheckBox _useDriverPropsChk = new JCheckBox(s_stringMgr.getString("ConnectionInternalFrame.userdriverprops"));
124:
125: /** Button that brings up the driver properties dialog. */
126: private final JButton _driverPropsBtn = new JButton(s_stringMgr
127: .getString("ConnectionInternalFrame.props"));
128:
129: private StatusBar _statusBar = new StatusBar();
130:
131: /**
132: * Ctor.
133: *
134: * @param app Application API.
135: * @param alias <TT>SQLAlias</TT> that we are going to connect to.
136: * @param handler Handler for internal frame actions.
137: *
138: * @throws IllegalArgumentException
139: * If <TT>null</TT> <TT>IApplication</TT>, <TT>ISQLAlias</TT>,
140: * or <TT>IConnectionInternalFrameHandler</TT> passed.
141: */
142: public ConnectionInternalFrame(IApplication app, ISQLAlias alias,
143: IHandler handler) {
144: super ("", true);
145: if (app == null) {
146: throw new IllegalArgumentException(
147: "Null IApplication passed");
148: }
149: if (alias == null) {
150: throw new IllegalArgumentException("Null ISQLAlias passed");
151: }
152: if (handler == null) {
153: throw new IllegalArgumentException(
154: "Null IConnectionInternalFrameHandler passed");
155: }
156:
157: _app = app;
158: _alias = alias;
159: _handler = handler;
160:
161: _sqlDriver = _app.getDataCache().getDriver(
162: _alias.getDriverIdentifier());
163: if (_sqlDriver == null) {
164: throw new IllegalStateException(s_stringMgr.getString(
165: "ConnectionInternalFrame.error.nodriver", _alias
166: .getName()));
167: }
168:
169: createGUI();
170: loadData();
171: pack();
172: }
173:
174: public void executed(final boolean connected) {
175: _connecting = false;
176: GUIUtils.processOnSwingEventThread(new Runnable() {
177: public void run() {
178: if (connected) {
179: dispose();
180: } else {
181: setStatusText(null);
182: _user.setEnabled(true);
183: _password.setEnabled(true);
184: _btnsPnl.setExecuting(false);
185: }
186: }
187: });
188: }
189:
190: /**
191: * If the alias specifies autologon then connect after the Dialog is visible.
192: *
193: * @param visible If <TT>true</TT> dialog is to be made visible.
194: */
195: public void setVisible(boolean visible) {
196: super .setVisible(visible);
197:
198: if (visible && _alias.isAutoLogon()) {
199: SwingUtilities.invokeLater(new Runnable() {
200: public void run() {
201: connect();
202: }
203: });
204: }
205: }
206:
207: /**
208: * Set the text in the status bar.
209: *
210: * @param text The text to place in the status bar.
211: */
212: public void setStatusText(String text) {
213: _statusBar.setText(text);
214: }
215:
216: /**
217: * Allow base class to create rootpane and add a couple
218: * of listeners for ENTER and ESCAPE to it.
219: */
220: protected JRootPane createRootPane() {
221: ActionListener escapeListener = new ActionListener() {
222: public void actionPerformed(ActionEvent actionEvent) {
223: ConnectionInternalFrame.this .dispose();
224: }
225: };
226:
227: ActionListener enterListener = new ActionListener() {
228: public void actionPerformed(ActionEvent actionEvent) {
229: ConnectionInternalFrame.this .connect();
230: }
231: };
232:
233: final JRootPane pane = super .createRootPane();
234:
235: KeyStroke ks = KeyStroke.getKeyStroke(KeyEvent.VK_ESCAPE, 0);
236: pane.registerKeyboardAction(escapeListener, ks,
237: WHEN_IN_FOCUSED_WINDOW);
238: ks = KeyStroke.getKeyStroke(KeyEvent.VK_ENTER, 0);
239: pane.registerKeyboardAction(enterListener, ks,
240: WHEN_IN_FOCUSED_WINDOW);
241:
242: return pane;
243: }
244:
245: /**
246: * Load data about selected alias into the UI.
247: */
248: private void loadData() {
249: if (SwingUtilities.isEventDispatchThread()) {
250: _loadData();
251: } else {
252: SwingUtilities.invokeLater(new Runnable() {
253: public void run() {
254: _loadData();
255: }
256: });
257: }
258: //loadDriverProperties();
259:
260: }
261:
262: private void _loadData() {
263: String userName = _alias.getUserName();
264: String password = _alias.getPassword();
265: _aliasName.setText(_alias.getName());
266: _driverName.setText(_sqlDriver.getName());
267: _url.setText(_alias.getUrl());
268: _user.setText(userName);
269: _password.setText(password);
270: // _useDriverPropsChk.setSelected(_alias.getUseDriverProperties());
271: // _driverPropsBtn.setEnabled(_useDriverPropsChk.isSelected());
272: // This is mainly for long URLs that cannot be fully
273: // displayed in the label.
274: _aliasName.setToolTipText(_aliasName.getText());
275: _driverName.setToolTipText(_driverName.getText());
276: _url.setToolTipText(_url.getText());
277: }
278:
279: private void connect() {
280: if (!_connecting) {
281: _connecting = true;
282: _btnsPnl.setExecuting(true);
283: setStatusText(s_stringMgr
284: .getString("ConnectionInternalFrame.connecting"));
285: _user.setEnabled(false);
286: _password.setEnabled(false);
287:
288: SQLDriverPropertyCollection driverProperties = _alias
289: .getDriverPropertiesClone();
290: if (!_alias.getUseDriverProperties()) {
291: driverProperties.clear();
292: }
293: _handler.performOK(this , _user.getText(), _password
294: .getText(), driverProperties);
295: }
296: }
297:
298: private void cancelConnect() {
299: if (_connecting) {
300: // abort first..
301: setStatusText(s_stringMgr
302: .getString("ConnectionInternalFrame.cancelling"));
303: _btnsPnl.enableCloseButton(false);
304: _handler.performCancelConnect(this );
305: _connecting = false;
306: dispose();
307: }
308: }
309:
310: private void createGUI() {
311: setDefaultCloseOperation(DISPOSE_ON_CLOSE);
312: GUIUtils.makeToolWindow(this , true);
313:
314: final String winTitle = s_stringMgr.getString(
315: "ConnectionInternalFrame.title", _alias.getName());
316: setTitle(winTitle);
317:
318: final JPanel content = new JPanel(new BorderLayout());
319: content.add(createMainPanel(), BorderLayout.CENTER);
320: content.add(_statusBar, BorderLayout.SOUTH);
321: setContentPane(content);
322:
323: // TODO:
324: // _btnsPnl.makeOKButtonDefault();
325: }
326:
327: /**
328: * Create the main panel
329: *
330: * @return main panel.
331: */
332: private Component createMainPanel() {
333: _user.setColumns(20);
334: _password.setColumns(20);
335:
336: _driverPropsBtn.addActionListener(new ActionListener() {
337: public void actionPerformed(ActionEvent evt) {
338: showDriverPropertiesDialog();
339: }
340: });
341:
342: _btnsPnl.addListener(new MyOkClosePanelListener());
343:
344: final FormLayout layout = new FormLayout(
345: // Columns
346: "right:pref, 8dlu, left:min(100dlu;pref):grow",
347: // Rows
348: "pref, 6dlu, pref, 6dlu, pref, 6dlu, pref, 6dlu, pref, 6dlu, "
349: + "pref, 6dlu, pref, 6dlu, pref, 3dlu, pref, 3dlu, pref");
350:
351: PanelBuilder builder = new PanelBuilder(layout);
352: CellConstraints cc = new CellConstraints();
353: builder.setDefaultDialogBorder();
354:
355: int y = 1;
356: builder.addSeparator(title, cc.xywh(1, y, 3, 1));
357:
358: y += 2;
359: builder.addLabel(s_stringMgr
360: .getString("ConnectionInternalFrame.alias"), cc
361: .xy(1, y));
362: builder.add(_aliasName, cc.xywh(3, y, 1, 1));
363:
364: y += 2;
365: builder.addLabel(s_stringMgr
366: .getString("ConnectionInternalFrame.driver"), cc.xy(1,
367: y));
368: builder.add(_driverName, cc.xywh(3, y, 1, 1));
369:
370: y += 2;
371: builder.addLabel(s_stringMgr
372: .getString("ConnectionInternalFrame.url"), cc.xy(1, y));
373: builder.add(_url, cc.xywh(3, y, 1, 1));
374:
375: y += 2;
376: builder
377: .addLabel(s_stringMgr
378: .getString("ConnectionInternalFrame.user"), cc
379: .xy(1, y));
380: builder.add(_user, cc.xywh(3, y, 1, 1));
381:
382: y += 2;
383: builder.addLabel(s_stringMgr
384: .getString("ConnectionInternalFrame.password"), cc.xy(
385: 1, y));
386: builder.add(_password, cc.xywh(3, y, 1, 1));
387:
388: y += 2;
389: _driverPropsBtn.setIcon(_app.getResources().getIcon(
390: SquirrelResources.IImageNames.ALIAS_PROPERTIES));
391: builder.add(_driverPropsBtn, cc.xywh(3, y, 1, 1));
392:
393: y += 2;
394: builder.addLabel(s_stringMgr
395: .getString("ConnectionInternalFrame.warningcapslock"),
396: cc.xywh(1, y, 3, 1));
397:
398: y += 2;
399: builder.addSeparator("", cc.xywh(1, y, 3, 1));
400:
401: y += 2;
402: builder.add(_btnsPnl, cc.xywh(1, y, 3, 1));
403:
404: // _useDriverPropsChk.addActionListener(new ActionListener()
405: // {
406: // public void actionPerformed(ActionEvent evt)
407: // {
408: // boolean useDriverProps = _useDriverPropsChk.isSelected();
409: // _driverPropsBtn.setEnabled(useDriverProps);
410: // if (useDriverProps)
411: // {
412: // loadDriverProperties();
413: // }
414: // }
415: // });
416:
417: // Set focus to password control if default user name has been setup.
418: addInternalFrameListener(new InternalFrameAdapter() {
419: private InternalFrameAdapter _this ;
420:
421: public void internalFrameActivated(InternalFrameEvent evt) {
422: _this = this ;
423: final String userName = _user.getText();
424: if (userName != null && userName.length() > 0) {
425: SwingUtilities.invokeLater(new Runnable() {
426: public void run() {
427: final String pw = _password.getText();
428: if (pw != null && pw.length() > 0) {
429: _btnsPnl.getOKButton().requestFocus();
430: } else {
431: _password.requestFocus();
432: }
433: ConnectionInternalFrame.this
434: .removeInternalFrameListener(_this );
435: }
436: });
437: }
438: }
439: });
440:
441: return builder.getPanel();
442: }
443:
444: private void showDriverPropertiesDialog() {
445: new AliasPropertiesCommand(_alias, _app).execute();
446: // final Frame owner = _app.getMainFrame();
447: // DriverPropertiesDialog.showDialog(owner, _props);
448: }
449:
450: // private void loadDriverProperties()
451: // {
452: // if (!_driverPropertiesLoaded)
453: // {
454: // if (_useDriverPropsChk.isSelected())
455: // {
456: // _driverPropertiesLoaded = true;
457: // try
458: // {
459: // final SQLDriverManager mgr = _app.getSQLDriverManager();
460: // final Driver jdbcDriver = mgr.getJDBCDriver(_sqlDriver.getIdentifier());
461: // if (jdbcDriver == null)
462: // {
463: // throw new BaseException(s_stringMgr.getString("ConnectionInternalFrame.error.cannotloaddriver"));
464: // }
465: //
466: // _props = _alias.getDriverPropertiesClone();
467: // DriverPropertyInfo[] infoAr = jdbcDriver.getPropertyInfo(_alias.getUrl(),
468: // new Properties());
469: // _props.applyDriverPropertynfo(infoAr);
470: // }
471: // catch (Exception ex)
472: // {
473: // String msg = s_stringMgr.getString("ConnectionInternalFrame.error.driverprops");
474: // s_log.error(msg, ex);
475: // _app.showErrorDialog(msg, ex);
476: // }
477: // }
478: // }
479: // }
480:
481: /**
482: * Listener to handle button events in OK/Close panel.
483: */
484: private final class MyOkClosePanelListener implements
485: IOkClosePanelListener {
486: public void okPressed(OkClosePanelEvent evt) {
487: ConnectionInternalFrame.this .connect();
488: }
489:
490: public void closePressed(OkClosePanelEvent evt) {
491: ConnectionInternalFrame.this .dispose();
492: }
493:
494: public void cancelPressed(OkClosePanelEvent evt) {
495: ConnectionInternalFrame.this.cancelConnect();
496: }
497: }
498: }
|