001/* An actor that converts Cartesian coordinates to polar form. 002 003 Copyright (c) 1998-2014 The Regents of the University of California. 004 All rights reserved. 005 Permission is hereby granted, without written agreement and without 006 license or royalty fees, to use, copy, modify, and distribute this 007 software and its documentation for any purpose, provided that the above 008 copyright notice and the following two paragraphs appear in all copies 009 of this software. 010 011 IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY 012 FOR DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES 013 ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF 014 THE UNIVERSITY OF CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF 015 SUCH DAMAGE. 016 017 THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, 018 INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 019 MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE 020 PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND THE UNIVERSITY OF 021 CALIFORNIA HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT, UPDATES, 022 ENHANCEMENTS, OR MODIFICATIONS. 023 024 PT_COPYRIGHT_VERSION_2 025 COPYRIGHTENDKEY 026 027 */ 028package ptolemy.actor.lib.conversions; 029 030import ptolemy.actor.TypedAtomicActor; 031import ptolemy.actor.TypedIOPort; 032import ptolemy.data.DoubleToken; 033import ptolemy.data.type.BaseType; 034import ptolemy.kernel.CompositeEntity; 035import ptolemy.kernel.util.IllegalActionException; 036import ptolemy.kernel.util.NameDuplicationException; 037 038/////////////////////////////////////////////////////////////////// 039/// CartesianToPolar 040 041/** 042 <p>Convert a Cartesian pair, which is represented by two double tokens (x and y), 043 to a polar form, which is also represented by two double tokens (magnitude 044 and angle). The angle is in radians. 045 </p><p> 046 The implementation uses java.lang.Math.atan2(double, double).</p> 047 @see java.lang.Math#atan2(double, double) 048 049 @author Michael Leung, Edward A. Lee, Paul Whitaker 050 @version $Id$ 051 @since Ptolemy II 1.0 052 @Pt.ProposedRating Green (pwhitake) 053 @Pt.AcceptedRating Green (pwhitake) 054 */ 055public class CartesianToPolar extends TypedAtomicActor { 056 /** Construct an actor with the given container and name. 057 * @param container The container. 058 * @param name The name of this actor. 059 * @exception IllegalActionException If the actor cannot be contained 060 * by the proposed container. 061 * @exception NameDuplicationException If the container already has an 062 * actor with this name. 063 */ 064 public CartesianToPolar(CompositeEntity container, String name) 065 throws NameDuplicationException, IllegalActionException { 066 super(container, name); 067 068 x = new TypedIOPort(this, "x", true, false); 069 x.setTypeEquals(BaseType.DOUBLE); 070 071 y = new TypedIOPort(this, "y", true, false); 072 y.setTypeEquals(BaseType.DOUBLE); 073 074 magnitude = new TypedIOPort(this, "magnitude", false, true); 075 magnitude.setTypeEquals(BaseType.DOUBLE); 076 077 angle = new TypedIOPort(this, "angle", false, true); 078 angle.setTypeEquals(BaseType.DOUBLE); 079 080 _attachText("_iconDescription", 081 "<svg>\n" + "<polygon points=\"-15,-15 15,15 15,-15 -15,15\" " 082 + "style=\"fill:white\"/>\n" + "</svg>\n"); 083 } 084 085 /////////////////////////////////////////////////////////////////// 086 //// public variables //// 087 088 /** The x coordinate of the input pair, which has type DoubleToken. */ 089 public TypedIOPort x; 090 091 /** The y coordinate of the input pair, which has type DoubleToken. */ 092 public TypedIOPort y; 093 094 /** The magnitude component of the output pair, which has type 095 DoubleToken. */ 096 public TypedIOPort magnitude; 097 098 /** The angle component of the output pair, which has type DoubleToken. */ 099 public TypedIOPort angle; 100 101 /////////////////////////////////////////////////////////////////// 102 //// public methods //// 103 104 /** Consume one double token from each of the two input ports (x and y), 105 * and output one new double token on each of the two output ports 106 * (magnitude and angle). The output is a polar form representation of 107 * the Cartesian pair given at the inputs. The angle is in radians. 108 * @exception IllegalActionException If there is no director. 109 */ 110 @Override 111 public void fire() throws IllegalActionException { 112 super.fire(); 113 double xValue = ((DoubleToken) x.get(0)).doubleValue(); 114 double yValue = ((DoubleToken) y.get(0)).doubleValue(); 115 116 double magnitudeValue = Math.sqrt(xValue * xValue + yValue * yValue); 117 double angleValue = Math.atan2(yValue, xValue); 118 119 magnitude.send(0, new DoubleToken(magnitudeValue)); 120 angle.send(0, new DoubleToken(angleValue)); 121 } 122 123 /** Return false if either of the input ports has no token, otherwise 124 * return what the superclass returns (presumably true). 125 * @exception IllegalActionException If there is no director. 126 */ 127 @Override 128 public boolean prefire() throws IllegalActionException { 129 if (!x.hasToken(0) || !y.hasToken(0)) { 130 return false; 131 } 132 133 return super.prefire(); 134 } 135}