我需要一个 JTextField 来插入十六进制字节。示例:“05 DE DD A9 4D 00 0C 5E”我已经尝试使用带有掩码“HH HH HH”的 JFormattedTextField + MaskFormatter,但这是一个固定掩码。我需要一个,可以“填满”。
我也尝试过 DocumentFilter,但这不允许我编辑完整的文本。只有插入的块被“过滤”。
你知道解决问题的另一种方法吗?
我需要一个 JTextField 来插入十六进制字节。示例:“05 DE DD A9 4D 00 0C 5E”我已经尝试使用带有掩码“HH HH HH”的 JFormattedTextField + MaskFormatter,但这是一个固定掩码。我需要一个,可以“填满”。
我也尝试过 DocumentFilter,但这不允许我编辑完整的文本。只有插入的块被“过滤”。
你知道解决问题的另一种方法吗?
问题解决了。
import java.awt.EventQueue;
import java.awt.Toolkit;
import javax.xml.bind.DatatypeConverter;
import javax.swing.*;
import javax.swing.event.DocumentEvent;
import javax.swing.event.DocumentListener;
public class HexTextField extends JTextField implements DocumentListener
{
private static final long serialVersionUID= -6694532039668603522L;
private boolean filtering= false;
public HexTextField()
{
super();
getDocument().addDocumentListener(this);
}
@Override
public void changedUpdate(DocumentEvent e)
{
filterText();
}
@Override
public void insertUpdate(DocumentEvent e)
{
filterText();
}
@Override
public void removeUpdate(DocumentEvent e)
{
filterText();
}
private void filterText()
{
if(filtering)
return;
filtering= true;
EventQueue.invokeLater(new Runnable()
{
@Override
public void run()
{
String input= getText().toUpperCase();
String filtered= "";
int index= 0;
// filter
for(int i= 0; i < input.length(); i++)
{
char c= input.charAt(i);
if("0123456789ABCDEF".indexOf(c) >= 0) // hex only
{
filtered+= c;
if(index++ % 2 == 1 && i != input.length() - 1)
filtered+= " "; // whitespace after each byte
}
}
// limit size
int maxBytes= 256;
if(filtered.length() > 3 * maxBytes)
{
filtered= filtered.substring(0, 3 * maxBytes);
Toolkit.getDefaultToolkit().beep();
}
setText(filtered);
filtering= false;
}
});
}
public byte[] getBytes()
{
String text= getText().replace(" ", "");
if(text.length() == 0)
return null;
if(text.length() % 2 == 1)
text= text.substring(0, text.length()-1) + "0" + text.charAt(text.length()-1);
byte[] bytes= DatatypeConverter.parseHexBinary(text);
if(bytes.length == 0)
return null;
return bytes;
}
}