001package jmri.util.swing; 002 003import java.awt.event.ActionEvent; 004import javax.swing.Icon; 005import org.slf4j.Logger; 006import org.slf4j.LoggerFactory; 007 008/** 009 * Abstract base for actions that will work with multiple JMRI GUIs. 010 * 011 * An opaque Object can be passed as a context, but null is also possible. 012 * 013 * <b>NOTE</b> Either 014 * {@link jmri.util.swing.JmriAbstractAction#actionPerformed(java.awt.event.ActionEvent)} 015 * or {@link jmri.util.swing.JmriAbstractAction#makePanel()} must be overridden 016 * by extending classes. 017 * 018 * @author Bob Jacobsen Copyright (C) 2010 019 */ 020abstract public class JmriAbstractAction extends javax.swing.AbstractAction { 021 022 protected WindowInterface.Hint hint = WindowInterface.Hint.DEFAULT; 023 protected WindowInterface wi; 024 protected Object context = null; 025 private final static Logger log = LoggerFactory.getLogger(JmriAbstractAction.class); 026 027 /** 028 * Enhanced constructor for placing the pane in various GUIs. 029 * 030 * @param name the name for the action; a value of null is ignored 031 * @param wi the window interface controlling how this action is displayed 032 */ 033 public JmriAbstractAction(String name, WindowInterface wi) { 034 super(name); 035 this.wi = wi; 036 if (wi == null) { 037 log.error("Cannot create action with null WindowInterface", new Exception()); 038 } 039 } 040 041 public JmriAbstractAction(String s, Icon i, WindowInterface wi) { 042 super(s, i); 043 this.wi = wi; 044 } 045 046 /** 047 * Set the context for this action. The context can be any object that an 048 * overriding class may need to complete an action. It is defined here to 049 * provide a common API for passing these objects in. 050 * 051 * @param context the context object 052 * @since 2.9.4 053 */ 054 public void setContext(Object context) { 055 this.context = context; 056 } 057 058 /** 059 * Original constructor for compatibility with older menus. Assumes SDI GUI. 060 * 061 * @param name the name for the action; a value of null is ignored 062 */ 063 public JmriAbstractAction(String name) { 064 super(name); 065 this.wi = new jmri.util.swing.sdi.JmriJFrameInterface(); 066 } 067 068 public void setWindowInterface(WindowInterface wi) { 069 this.wi = wi; 070 } 071 072 public void setName(String name) { 073 putValue(javax.swing.Action.NAME, name); 074 } 075 076 @Override 077 public String toString() { 078 return (String) getValue(javax.swing.Action.NAME); 079 } 080 081 public JmriAbstractAction setHint(WindowInterface.Hint hint) { 082 this.hint = hint; 083 return this; 084 } 085 086 @Override 087 public void actionPerformed(ActionEvent e) { 088 // we have to make a new panel if we don't have one yet 089 // we don't make a new panel if the window interface is 090 // single instance (not multiple instance), 091 // or if the existing panel is single instance (not multiple instance) 092 if (cache == null 093 || (wi.multipleInstances() && cache.isMultipleInstances())) { 094 try { 095 cache = makePanel(); 096 } catch (Exception ex) { 097 log.error("Exception creating panel", ex); 098 return; 099 } 100 if (cache == null) { 101 log.error("Unable to make panel"); 102 return; 103 } 104 } 105 106 wi.show(cache, this, hint); // no real context, this is new content 107 } 108 109 public void dispose() { 110 if (cache != null) { 111 cache.dispose(); 112 cache = null; 113 } 114 } 115 JmriPanel cache = null; 116 117 // A crude method to set a parameter in a given window when loading from the xml file 118 public void setParameter(String parameter, String value) { 119 } 120 121 // A method to allow named parameters to be passed in. 122 // Note that if value is a String, setParameter(String, String) needs to be 123 // implemented (for reasons I do not understand jmri.util.swing.GuiUtilBase 124 // will not call this method with a String parameter for value) 125 public void setParameter(String parameter, Object value) { 126 } 127 128 abstract public JmriPanel makePanel(); 129 130}