001 /*
002 * $Id: LinkModelAction.java 3294 2009-03-11 10:50:52Z kleopatra $
003 *
004 * Copyright 2004 Sun Microsystems, Inc., 4150 Network Circle,
005 * Santa Clara, California 95054, U.S.A. All rights reserved.
006 *
007 * This library is free software; you can redistribute it and/or
008 * modify it under the terms of the GNU Lesser General Public
009 * License as published by the Free Software Foundation; either
010 * version 2.1 of the License, or (at your option) any later version.
011 *
012 * This library is distributed in the hope that it will be useful,
013 * but WITHOUT ANY WARRANTY; without even the implied warranty of
014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
015 * Lesser General Public License for more details.
016 *
017 * You should have received a copy of the GNU Lesser General Public
018 * License along with this library; if not, write to the Free Software
019 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
020 */
021 package org.jdesktop.swingx.hyperlink;
022
023 import java.awt.event.ActionEvent;
024 import java.awt.event.ActionListener;
025 import java.beans.PropertyChangeEvent;
026 import java.beans.PropertyChangeListener;
027
028 import javax.swing.Action;
029
030
031 /**
032 * Specialized LinkAction for a target of type {@link LinkModel}.
033 * <p>
034 *
035 * This action delegates actionPerformed to vistingDelegate.
036 *
037 * PENDING: move to swingx package?
038 *
039 * @author Jeanette Winzenburg
040 */
041 public class LinkModelAction<T extends LinkModel> extends AbstractHyperlinkAction<T> {
042
043 private ActionListener delegate;
044 public static final String VISIT_ACTION = "visit";
045 private PropertyChangeListener linkListener;
046
047
048 public LinkModelAction() {
049 this((T) null);
050 }
051
052 public LinkModelAction(ActionListener visitingDelegate) {
053 this(null, visitingDelegate);
054 }
055
056 public LinkModelAction(T target) {
057 this(target, null);
058 }
059
060 public LinkModelAction(T target, ActionListener visitingDelegate) {
061 super(target);
062 setVisitingDelegate(visitingDelegate);
063 }
064
065 /**
066 * The delegate to invoke on actionPerformed.
067 * <p>
068 * The delegates actionPerformed is invoked with an ActionEvent
069 * having the target as source. Delegates are expected to
070 * cope gracefully with the T.
071 * <p>
072 *
073 * PENDING: JW - How to formalize?
074 *
075 * @param delegate the action invoked on the target.
076 */
077 public void setVisitingDelegate(ActionListener delegate) {
078 this.delegate = delegate;
079 }
080
081 /**
082 * This action delegates to the visitingDelegate if both
083 * delegate and target are != null, does nothing otherwise.
084 * The actionEvent carries the target as source.
085 *
086 * PENDING: pass through a null target? - most probably!
087 *
088 *
089 *
090 */
091 public void actionPerformed(ActionEvent e) {
092 if ((delegate != null) && (getTarget() != null)) {
093 delegate.actionPerformed(new ActionEvent(getTarget(), ActionEvent.ACTION_PERFORMED, VISIT_ACTION));
094 }
095
096 }
097
098 /**
099 * installs a propertyChangeListener on the target and
100 * updates the visual properties from the target.
101 */
102 @Override
103 protected void installTarget() {
104 if (getTarget() != null) {
105 getTarget().addPropertyChangeListener(getTargetListener());
106 }
107 updateFromTarget();
108 }
109
110 /**
111 * removes the propertyChangeListener. <p>
112 *
113 * Implementation NOTE: this does not clean-up internal state! There is
114 * no need to because updateFromTarget handles both null and not-null
115 * targets. Hmm...
116 *
117 */
118 @Override
119 protected void uninstallTarget() {
120 if (getTarget() == null) return;
121 getTarget().removePropertyChangeListener(getTargetListener());
122 }
123
124 protected void updateFromTarget() {
125 if (getTarget() != null) {
126 putValue(Action.NAME, getTarget().getText());
127 putValue(Action.SHORT_DESCRIPTION, getTarget().getURL().toString());
128 putValue(VISITED_KEY, new Boolean(getTarget().getVisited()));
129 } else {
130 Object[] keys = getKeys();
131 if (keys == null) return;
132 for (int i = 0; i < keys.length; i++) {
133 putValue(keys[i].toString(), null);
134 }
135 }
136 }
137
138 private PropertyChangeListener getTargetListener() {
139 if (linkListener == null) {
140 linkListener = new PropertyChangeListener() {
141
142 public void propertyChange(PropertyChangeEvent evt) {
143 updateFromTarget();
144 }
145
146 };
147 }
148 return linkListener;
149 }
150
151
152 }