/*******************************************************************************
* This file is part of logisim-evolution.
*
* logisim-evolution 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.
*
* logisim-evolution 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 logisim-evolution. If not, see <http://www.gnu.org/licenses/>.
*
* Original code by Carl Burch (http://www.cburch.com), 2011.
* Subsequent modifications by :
* + Haute École Spécialisée Bernoise
* http://www.bfh.ch
* + Haute École du paysage, d'ingénierie et d'architecture de Genève
* http://hepia.hesge.ch/
* + Haute École d'Ingénierie et de Gestion du Canton de Vaud
* http://www.heig-vd.ch/
* The project is currently maintained by :
* + REDS Institute - HEIG-VD
* Yverdon-les-Bains, Switzerland
* http://reds.heig-vd.ch
*******************************************************************************/
package com.cburch.logisim.std.base;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Rectangle;
import com.cburch.logisim.comp.TextField;
import com.cburch.logisim.data.Attribute;
import com.cburch.logisim.data.AttributeOption;
import com.cburch.logisim.data.AttributeSet;
import com.cburch.logisim.data.Attributes;
import com.cburch.logisim.data.Bounds;
import com.cburch.logisim.data.Location;
import com.cburch.logisim.instance.Instance;
import com.cburch.logisim.instance.InstanceFactory;
import com.cburch.logisim.instance.InstancePainter;
import com.cburch.logisim.instance.InstanceState;
import com.cburch.logisim.util.GraphicsUtil;
public class Text extends InstanceFactory {
public static Attribute<String> ATTR_TEXT = Attributes.forString("text",
Strings.getter("textTextAttr"));
public static Attribute<Font> ATTR_FONT = Attributes.forFont("font",
Strings.getter("textFontAttr"));
public static Attribute<AttributeOption> ATTR_HALIGN = Attributes
.forOption(
"halign",
Strings.getter("textHorzAlignAttr"),
new AttributeOption[] {
new AttributeOption(Integer
.valueOf(TextField.H_LEFT), "left", Strings
.getter("textHorzAlignLeftOpt")),
new AttributeOption(Integer
.valueOf(TextField.H_RIGHT), "right",
Strings.getter("textHorzAlignRightOpt")),
new AttributeOption(Integer
.valueOf(TextField.H_CENTER), "center",
Strings.getter("textHorzAlignCenterOpt")), });
public static Attribute<AttributeOption> ATTR_VALIGN = Attributes
.forOption(
"valign",
Strings.getter("textVertAlignAttr"),
new AttributeOption[] {
new AttributeOption(Integer
.valueOf(TextField.V_TOP), "top", Strings
.getter("textVertAlignTopOpt")),
new AttributeOption(Integer
.valueOf(TextField.V_BASELINE), "base",
Strings.getter("textVertAlignBaseOpt")),
new AttributeOption(Integer
.valueOf(TextField.V_BOTTOM), "bottom",
Strings.getter("textVertAlignBottomOpt")),
new AttributeOption(Integer
.valueOf(TextField.H_CENTER), "center",
Strings.getter("textVertAlignCenterOpt")), });
public static final Text FACTORY = new Text();
private Text() {
super("Text", Strings.getter("textComponent"));
setIconName("text.gif");
setShouldSnap(false);
}
private void configureLabel(Instance instance) {
TextAttributes attrs = (TextAttributes) instance.getAttributeSet();
Location loc = instance.getLocation();
instance.setTextField(ATTR_TEXT, ATTR_FONT, loc.getX(), loc.getY(),
attrs.getHorizontalAlign(), attrs.getVerticalAlign());
}
//
// methods for instances
//
@Override
protected void configureNewInstance(Instance instance) {
configureLabel(instance);
instance.addAttributeListener();
}
@Override
public AttributeSet createAttributeSet() {
return new TextAttributes();
}
private Bounds estimateBounds(TextAttributes attrs) {
// TODO - you can imagine being more clever here
String text = attrs.getText();
if (text == null || text.length() == 0)
return Bounds.EMPTY_BOUNDS;
int size = attrs.getFont().getSize();
int h = size;
int w = size * text.length() / 2;
int ha = attrs.getHorizontalAlign();
int va = attrs.getVerticalAlign();
int x;
int y;
if (ha == TextField.H_LEFT) {
x = 0;
} else if (ha == TextField.H_RIGHT) {
x = -w;
} else {
x = -w / 2;
}
if (va == TextField.V_TOP) {
y = 0;
} else if (va == TextField.V_CENTER) {
y = -h / 2;
} else {
y = -h;
}
return Bounds.create(x, y, w, h);
}
@Override
public Bounds getOffsetBounds(AttributeSet attrsBase) {
TextAttributes attrs = (TextAttributes) attrsBase;
String text = attrs.getText();
if (text == null || text.equals("")) {
return Bounds.EMPTY_BOUNDS;
} else {
Bounds bds = attrs.getOffsetBounds();
if (bds == null) {
bds = estimateBounds(attrs);
attrs.setOffsetBounds(bds);
}
return bds == null ? Bounds.EMPTY_BOUNDS : bds;
}
}
@Override
public boolean HDLSupportedComponent(String HDLIdentifier,
AttributeSet attrs) {
return true;
}
@Override
protected void instanceAttributeChanged(Instance instance, Attribute<?> attr) {
if (attr == ATTR_HALIGN || attr == ATTR_VALIGN) {
configureLabel(instance);
}
}
//
// graphics methods
//
@Override
public void paintGhost(InstancePainter painter) {
TextAttributes attrs = (TextAttributes) painter.getAttributeSet();
String text = attrs.getText();
if (text == null || text.equals(""))
return;
int halign = attrs.getHorizontalAlign();
int valign = attrs.getVerticalAlign();
Graphics g = painter.getGraphics();
Font old = g.getFont();
g.setFont(attrs.getFont());
GraphicsUtil.drawText(g, text, 0, 0, halign, valign);
String textTrim = text.endsWith(" ") ? text.substring(0,
text.length() - 1) : text;
Bounds newBds;
if (textTrim.equals("")) {
newBds = Bounds.EMPTY_BOUNDS;
} else {
Rectangle bdsOut = GraphicsUtil.getTextBounds(g, textTrim, 0, 0,
halign, valign);
newBds = Bounds.create(bdsOut).expand(4);
}
if (attrs.setOffsetBounds(newBds)) {
Instance instance = painter.getInstance();
if (instance != null)
instance.recomputeBounds();
}
g.setFont(old);
}
@Override
public void paintInstance(InstancePainter painter) {
Location loc = painter.getLocation();
int x = loc.getX();
int y = loc.getY();
Graphics g = painter.getGraphics();
g.translate(x, y);
g.setColor(Color.BLACK);
paintGhost(painter);
g.translate(-x, -y);
}
@Override
public void propagate(InstanceState state) {
}
}