you helped me a lot. After testing a few examples posted here, I chose to create a component. See the code below.
package br.com.linu.vectortown.base.screen.textfield;
import java.awt.Color;
import java.awt.Point;
import java.awt.Rectangle;
import java.io.Serializable;
import br.com.linu.vectortown.base.screen.button.command.ICommand;
import br.com.linu.vectortown.base.screen.button.command.ISendCommand;
import br.com.linu.vectortown.base.screen.font.GameFont;
import br.com.linu.vectortown.base.screen.graphics.IGenericGraphics;
import br.com.linu.vectortown.base.util.PropertiesUtil;
public class GameTextField implements Serializable {
private static final long serialVersionUID = -8273087631607158422L;
private static final String CURSOR = "|";
private StringBuffer buffer;
private String showableText;
private int index;
private GameFont font;
private int maxLength;
private float alpha;
private Rectangle rectangle;
private Point textPoint;
private String validCharacters;
private int padding;
private int cursorDelay;
private int countDelay;
private boolean cursor;
private int cursorLength;
private boolean focus;
private ICommand clickedCommand;
private ISendCommand returnKeyCommand;
private ICommand escapeKeyCommand;
public GameTextField(GameFont font, Rectangle rectangle, int maxLength) {
/* Get default parameters */
this.validCharacters = PropertiesUtil.INSTANCE.valorPor("game.text.field.valid.characters");
this.padding = PropertiesUtil.INSTANCE.inteiroPor("game.text.field.padding");
this.cursorDelay = PropertiesUtil.INSTANCE.inteiroPor("game.text.field.cursor.delay");
this.alpha = PropertiesUtil.INSTANCE.floatPor("game.boxlog.text.field.background.alpha");
/* Set attributes with constructor parameters */
this.font = font;
this.rectangle = rectangle;
/* Set text point */
int x = this.rectangle.x + this.padding;
int y = this.rectangle.y +
this.font.getSpacing( this.validCharacters ).height +
this.font.getFineTuning() -
this.padding;
this.textPoint = new Point( x , y );
/* Create variables to control buffer */
this.buffer = new StringBuffer();
this.showableText = "";
this.maxLength = maxLength;
this.clearIndex();
/* Create variables to control cursor */
this.countDelay = 0;
this.cursor = false;
this.cursorLength = this.font.getSpacing( CURSOR ).width;
/* Starts without focus */
this.focus = false;
}
private void clearTextField() {
this.focus = false;
this.buffer = new StringBuffer();
this.showableText = "";
this.clearIndex();
}
private int getAdjustedTextWidth(String text) {
return font.getSpacing(text).width + cursorLength + (2 * padding);
}
public void setClickedCommand(ICommand command) {
this.clickedCommand = command;
}
public void setReturnKeyCommand(ISendCommand command) {
this.returnKeyCommand = command;
}
public void setEscapeKeyCommand(ICommand command) {
this.escapeKeyCommand = command;
}
public synchronized boolean wasClicked(int mouseX, int mouseY) {
focus = rectangle.contains( new Point( mouseX , mouseY ) );
if ( focus ) {
this.clickedCommand.execute();
}
return focus;
}
public synchronized void onFocus() {
focus = true;
}
/**
* ENTER
*/
public synchronized void returnKey() {
if ( buffer.length() > 0 ) {
String value = this.buffer.toString();
clearTextField();
this.returnKeyCommand.setParameters(value);
this.returnKeyCommand.execute();
} else {
clearTextField();
this.escapeKeyCommand.execute();
}
}
/**
* ESC
*/
public synchronized void escapeKey() {
clearTextField();
this.escapeKeyCommand.execute();
}
private void clearIndex() {
this.index = 0;
}
private int getIndex() {
return index;
}
private void increaseIndex() {
index++;
}
public synchronized void delete() {
if ( buffer.length() > 0 ) {
clearIndex();
buffer.deleteCharAt( buffer.length() - 1 );
/* Get showable text with index */
showableText = buffer.substring( getIndex() , buffer.length() );
/* Adjust showable text if necessary */
while ( getAdjustedTextWidth(showableText) > rectangle.width ) {
increaseIndex();
showableText = buffer.substring( getIndex() , buffer.length() );
}
}
}
public synchronized void add(char character) {
/* Validate size */
if ( buffer.length() >= maxLength ) {
return;
}
/* Validate character */
if ( validCharacters.indexOf( character ) == -1 ) {
return;
}
/* Add char in buffer */
buffer.append( character );
/* Get showable text with index */
showableText = buffer.substring( getIndex() , buffer.length() );
/* Adjust showable text if necessary */
while ( getAdjustedTextWidth(showableText) > rectangle.width ) {
increaseIndex();
showableText = buffer.substring( getIndex() , buffer.length() );
}
}
public synchronized void draw(IGenericGraphics graphics) {
if ( focus ) {
/* Draw component */
graphics.drawFilledRectangle(Color.white, rectangle, alpha);
/* Verifier if can draw cursor */
countDelay++;
countDelay = countDelay % cursorDelay;
if ( countDelay == 0 ) {
cursor = !cursor;
}
/* Set text to draw */
String text = showableText + ( ( cursor ) ? CURSOR : "" );
/* Draw */
graphics.drawText(font, textPoint.x, textPoint.y, text);
}
}
}
Sorry if I did not put any code in question. What I really needed was a TextField any that ran entirely on a Graphics2D. In this application I get the Graphics2D of JPanel and I change their behavior manually (with keys and mouse listeners). When I put a JTextField in this JPanel, it did not work normally. This was the problem.
As I did not get a good alternative, I decided to create a custom component (code above). What matters is the methods draw() and add(). In the draw() method I drew a rectangle and the text that was entered character by character in the add() method. For now this is working ...
Thanks for the help everyone!