001/* An action to toggle displaying all port names. 002 * 003 * Copyright (c) 2011 The Regents of the University of California. 004 * All rights reserved. 005 * 006 * '$Author: crawl $' 007 * '$Date: 2011-10-04 21:11:45 +0000 (Tue, 04 Oct 2011) $' 008 * '$Revision: 28755 $' 009 * 010 * Permission is hereby granted, without written agreement and without 011 * license or royalty fees, to use, copy, modify, and distribute this 012 * software and its documentation for any purpose, provided that the above 013 * copyright notice and the following two paragraphs appear in all copies 014 * of this software. 015 * 016 * IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY 017 * FOR DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES 018 * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF 019 * THE UNIVERSITY OF CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF 020 * SUCH DAMAGE. 021 * 022 * THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, 023 * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 024 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE 025 * PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND THE UNIVERSITY OF 026 * CALIFORNIA HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT, UPDATES, 027 * ENHANCEMENTS, OR MODIFICATIONS. 028 * 029 */ 030 031package org.kepler.gui; 032 033import java.awt.event.ActionEvent; 034import java.util.Collections; 035import java.util.List; 036import java.util.Map; 037import java.util.WeakHashMap; 038 039import ptolemy.actor.gui.PtolemyFrame; 040import ptolemy.actor.gui.TableauFrame; 041import ptolemy.data.BooleanToken; 042import ptolemy.data.Token; 043import ptolemy.data.expr.Parameter; 044import ptolemy.kernel.CompositeEntity; 045import ptolemy.kernel.Entity; 046import ptolemy.kernel.Port; 047import ptolemy.kernel.util.Attribute; 048import ptolemy.kernel.util.IllegalActionException; 049import ptolemy.kernel.util.NamedObj; 050import ptolemy.moml.MoMLChangeRequest; 051import ptolemy.util.MessageHandler; 052import ptolemy.vergil.toolbox.FigureAction; 053 054/** An action to toggle displaying all port names. 055 * 056 * @author Daniel Crawl 057 * @version $Id: ToggleAllPortNamesAction.java 28755 2011-10-04 21:11:45Z crawl $ 058 * 059 */ 060 061public class ToggleAllPortNamesAction extends FigureAction { 062 063 public ToggleAllPortNamesAction(TableauFrame frame) { 064 super(""); 065 _parent = frame; 066 } 067 068 public void actionPerformed(ActionEvent event) { 069 super.actionPerformed(event); 070 071 NamedObj model = ((PtolemyFrame)_parent).getModel().toplevel(); 072 073 // see if we've already toggled for this model 074 Boolean showNames = _modelMap.get(model); 075 if(showNames == null) 076 { 077 showNames = Boolean.TRUE; 078 } 079 080 // toggle the names 081 _togglePortNames((Entity)model, showNames.booleanValue()); 082 083 // add this model to the map 084 _modelMap.put(model, !showNames.booleanValue()); 085 086 // perform an empty change request to repaint the canvas 087 MoMLChangeRequest change = new MoMLChangeRequest(model, model, "<group></group>"); 088 change.setPersistent(true); 089 model.requestChange(change); 090 } 091 092 /** Toggle the port names for an entity and any contained entities. */ 093 private void _togglePortNames(Entity entity, boolean showNames) 094 { 095 List<?> portList = entity.portList(); 096 for(Object obj : portList) 097 { 098 final Port port = (Port)obj; 099 final boolean isSet = _isPropertySet(port, "_showName"); 100 final boolean isHidden = _isPropertySet(port, "_hide"); 101 102 if(showNames && !isSet && !isHidden) 103 { 104 try { 105 new Parameter(port, "_showName", BooleanToken.TRUE); 106 } catch (Exception e) { 107 MessageHandler.error("Unable to show port name for " + 108 port.getFullName(), e); 109 } 110 } 111 else if(!showNames && isSet) 112 { 113 try { 114 port.getAttribute("_showName").setContainer(null); 115 } catch (Exception e) { 116 MessageHandler.error("Unable to remove _showName for " + 117 port.getFullName(), e); 118 } 119 } 120 } 121 122 // recursively toggle port names of contained entities 123 if(entity instanceof CompositeEntity) 124 { 125 List<?> entityList = ((CompositeEntity)entity).entityList(); 126 for(Object entityObj : entityList) 127 { 128 _togglePortNames((Entity)entityObj, showNames); 129 } 130 } 131 } 132 133 /** Return true if the property of the specified name is set for 134 * the specified object. A property is specified if the specified 135 * object contains an attribute with the specified name and that 136 * attribute is either not a boolean-valued parameter, or it is a 137 * boolean-valued parameter with value true. 138 * FIXME copied from PortConfigurerDialog 139 * @param object The object. 140 * @param name The property name. 141 * @return True if the property is set. 142 */ 143 private boolean _isPropertySet(NamedObj object, String name) { 144 Attribute attribute = object.getAttribute(name); 145 146 if (attribute == null) { 147 return false; 148 } 149 150 if (attribute instanceof Parameter) { 151 try { 152 Token token = ((Parameter) attribute).getToken(); 153 154 if (token instanceof BooleanToken) { 155 if (!((BooleanToken) token).booleanValue()) { 156 return false; 157 } 158 } 159 } catch (IllegalActionException e) { 160 // Ignore, using default of true. 161 } 162 } 163 164 return true; 165 } 166 167 /** The parent frame. */ 168 private TableauFrame _parent; 169 170 /** A mapping from model to current toggle value. Each model will be toggled 171 * independently. 172 */ 173 private static Map<NamedObj,Boolean> _modelMap = 174 Collections.synchronizedMap(new WeakHashMap<NamedObj,Boolean>()); 175}