⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 layoutlib.java

📁 The ElectricTM VLSI Design System is an open-source Electronic Design Automation (EDA) system that c
💻 JAVA
📖 第 1 页 / 共 3 页
字号:
/* -*- tab-width: 4 -*- * * Electric(tm) VLSI Design System * * File: LayoutLib.java * * Copyright (c) 2003 Sun Microsystems and Static Free Software * * Electric(tm) is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or * (at your option) any later version. * * Electric(tm) is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with Electric(tm); see the file COPYING.  If not, write to * the Free Software Foundation, Inc., 59 Temple Place, Suite 330, * Boston, Mass 02111-1307, USA. */package com.sun.electric.tool.generator.layout;import java.awt.geom.AffineTransform;import java.awt.geom.Point2D;import java.awt.geom.Rectangle2D;import java.net.URL;import java.util.ArrayList;import java.util.Collection;import java.util.Iterator;import com.sun.electric.database.geometry.DBMath;import com.sun.electric.database.geometry.EPoint;import com.sun.electric.database.geometry.Orientation;import com.sun.electric.database.geometry.Poly;import com.sun.electric.database.hierarchy.Cell;import com.sun.electric.database.hierarchy.Export;import com.sun.electric.database.hierarchy.Library;import com.sun.electric.database.prototype.NodeProto;import com.sun.electric.database.prototype.PortCharacteristic;import com.sun.electric.database.prototype.PortProto;import com.sun.electric.database.text.TextUtils;import com.sun.electric.database.topology.ArcInst;import com.sun.electric.database.topology.Connection;import com.sun.electric.database.topology.NodeInst;import com.sun.electric.database.topology.PortInst;import com.sun.electric.technology.ArcProto;import com.sun.electric.technology.Layer;import com.sun.electric.technology.SizeOffset;import com.sun.electric.technology.Technology;import com.sun.electric.tool.io.FileType;import com.sun.electric.tool.io.input.LibraryFiles;import com.sun.electric.tool.io.output.Output;import com.sun.electric.tool.user.ActivityLogger;import com.sun.electric.tool.user.dialogs.OpenFile;/* * The LayoutLib class provides an assortment of methods that I * found to be useful for programatic layout generation. */public class LayoutLib {	// ---------------------------- public data ------------------------------	/** Use the default size. When a width or height argument has this	 * value the object should be created with its default	 * dimension. Note that -DEF_SIZE is also a legal	 * constant. Negative dimensions specify mirroring for certain	 * methods. */	public static final double DEF_SIZE = Double.POSITIVE_INFINITY;	public static enum Corner {		TL, TR, BL, BR;	}	// ---------------------------- public methods ---------------------------	/**	 * Print a message, dump a stack trace, and throw a RuntimeException if 	 * errorHasOccurred argument is true.	 *	 * @param errorHasOccurred indicates a runtime error has been detected	 * @param msg the message to print when an error occurs	 * @throws RuntimeException if errorHasOccurred is true	 */	public static void error(boolean errorHasOccurred, String msg) {		if (!errorHasOccurred) return;		RuntimeException e = new RuntimeException(msg);		// The following prints a stack trace on the console        ActivityLogger.logException(e);		// The following prints a stack trace in the Electric messages window		throw e;	}	/** 	 * Open a library for reading. If a library is	 * already open then return it. Otherwise look for the library	 * file named libFileName and open that library.	 * 	 * @param libFileName the fully qualified path name of the Library	 * file on disk	 * @return the open Library or null if it can't be found	 */	public static Library openLibForRead(String libFileName) {		URL libFileURL = TextUtils.makeURLToFile(libFileName);		String libName = TextUtils.getFileNameWithoutExtension(libFileURL);		Library lib = Library.findLibrary(libName);		FileType type = OpenFile.getOpenFileType(libFileName, FileType.DEFAULTLIB);		if (lib==null) {			lib = LibraryFiles.readLibrary(libFileURL, null, type, false);		}		error(lib==null, "can't open Library for reading: "+libFileName);		return lib;	}	/**	 * Open a library for modification. If a library named libName is	 * already open then return it. Otherwise look for the file named:	 * libFileName and open that library. Finally, if all else fails	 * create a new Library and return it.	 *	 * @param libName the name of the Library	 * file on disk	 * @return the desired library	 */	// This doesn't work anymore.//	public static Library openLibForModify(String libName, String libFileName) {//		// return an open Library if it exists//		Library lib = Library.findLibrary(libName);//		if (lib!=null)  return lib;////		// open a Library file if it exists//		URL libFileURL = TextUtils.makeURLToFile(libFileName);//		lib = Input.readLibrary(libFileURL, OpenFile.Type.ELIB);//		if (lib!=null)  return lib;//		//		// create a new Library//		lib = Library.newInstance(libName, libFileURL);////		error(lib==null, "can't open Library for modify: "+libName);//		return lib;//	}	public static Library openLibForWrite(String libName) {		// return an open Library if it exists		Library lib = Library.findLibrary(libName);		if (lib!=null)  return lib;		// create a new Library		lib = Library.newInstance(libName, null);        URL libURL = TextUtils.makeURLToFile(libName);        lib.setLibFile(libURL);		error(lib==null, "can't open Library for modify: "+libName);		return lib;	}	/**	 * Write a library in JELIB format.	 * @param lib the library to be written.	 */	public static void writeLibrary(Library lib) {		Output.writeLibrary(lib, FileType.JELIB, false, false, false);	}	/**     * Get the width of an ArcInst. The getArcInstWidth method differs     * from ArcInst.getLambdaFullWidth() in that it subtracts off the "width     * offset". Hence, getArcInstWidth returns a width that matches     * that reported by the GUI.     *      * @param ai the ArcInst whose width is reported     * @return the width of the ArcInst.     */	public static double getArcInstWidth(ArcInst ai) {		double w = ai.getLambdaBaseWidth();		return DBMath.round(w);	}	/** Get the default width of a NodeProto. The getNodeProtoWidth	 * method differs from NodeProto.getDefWidth in that it subtracts	 * off the "width offset". Hence getNodeProtoWidth returns a width	 * that matches that reported by the GUI.	 *	 * @param np the NodeProto we want the width of.	 * @return the width of the NodeProto. */	public static double getNodeProtoWidth(NodeProto np) {		SizeOffset so = np.getProtoSizeOffset();		double w = np.getDefWidth() - so.getLowXOffset() - so.getHighXOffset();		return DBMath.round(w);	}	/** Get the default height of a NodeProto. The getNodeProtoHeight	 * method differs from NodeProto.getDefHeight in that it subtracts	 * off the "height offset". Hence getNodeProtoHeight returns a	 * height that matches that reported by the GUI.	 *	 * @param np the NodeProto we want the height of	 * @return the height of the NodeProto */	public static double getNodeProtoHeight(NodeProto np) {		SizeOffset so = np.getProtoSizeOffset();		double h = np.getDefHeight() - so.getLowYOffset() - so.getHighYOffset();		return DBMath.round(h);	}	private static void prln(String msg) {System.out.println(msg);}	/**	 * Find the width of the widest wire connected hierarchically to port.	 *	 * @param port the PortInst to check for attached wires.	 * @return the width of the widest wire. This width excludes the	 * "width offset" so it matches the width reported by the GUI.	 * If no wire is attached to port then return DEF_SIZE.	 */	public static double widestWireWidth(PortInst port) {//		NodeInst ni = port.getNodeInst();		PortProto pp = port.getPortProto();		double maxWid = -1;		for (Iterator<ArcInst> arcs=getArcInstsOnPortInst(port); arcs.hasNext();) {			ArcInst ai = arcs.next();			//prln("    arc width: "+getArcInstWidth(ai));			maxWid = Math.max(maxWid, getArcInstWidth(ai));		}		if (pp instanceof Export) {			double lowerMax = widestWireWidth(((Export)pp).getOriginalPort());			if (lowerMax!=DEF_SIZE)  maxWid = Math.max(maxWid, lowerMax);		}        if (maxWid < 0) return DEF_SIZE;		return DBMath.round(maxWid);	}	/** Return a list of ArcInsts attached to PortInst, pi.	 * @param pi PortInst on which to find attached ArcInsts. */	public static Iterator<ArcInst> getArcInstsOnPortInst(PortInst pi) {		ArrayList<ArcInst> arcs = new ArrayList<ArcInst>();//		NodeInst ni = pi.getNodeInst();		for (Iterator<Connection> it=pi.getConnections(); it.hasNext();) {			Connection c = it.next();			arcs.add(c.getArc());		}//		for (Iterator it=ni.getConnections(); it.hasNext();) {//			Connection c = it.next();//			if (c.getPortInst()==pi)  arcs.add(c.getArc());//		}		return arcs.iterator();	}	/** The center returned by bounds might have a slight amount of rounding	 * error. Compensate for this by always rounding coordinates to a 103-4	 * lambda grid when reading and writing the database. */	public static double roundCenterX(PortInst pi) {        return pi.getCenter().getX();//		return DBMath.round(pi.getBounds().getCenterX()); new way avoids rounding here	}	public static double roundCenterY(PortInst pi) {        return pi.getCenter().getY();//		return DBMath.round(pi.getBounds().getCenterY());	}    public static Rectangle2D calculateNodeInst(NodeProto np,                                                double x, double y,                                                double width, double height)    {		if (np instanceof Cell) {			width = (width<0 ? -1 : 1) * np.getDefWidth();			height = (height<0 ? -1 : 1) * np.getDefHeight();		} else {			SizeOffset so = np.getProtoSizeOffset();			// Take the default width or height if that's what the user wants.			// Otherwise adjust the user-specified width or height by the			// SizeOffset.			double signW = width<0 ? -1 : 1;			if (width==DEF_SIZE || width==-DEF_SIZE) {				width = signW * np.getDefWidth();			} else {				double hi = so.getHighXOffset();				double lo = so.getLowXOffset();				error(lo!=hi, "asymmetric X offset");				width = signW * (Math.abs(width) + hi+lo);			}			double signH = height<0 ? -1 : 1;			if (height==DEF_SIZE || height==-DEF_SIZE) {				height = signH * np.getDefHeight();			} else {				double hi = so.getHighYOffset();				double lo = so.getLowYOffset();				error(lo!=hi, "asymmetric Y offset");				height = signH * (Math.abs(height) + hi+lo);			}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -