有没有一种方便的方法来添加过滤器来输入scala.swing.TextComponent,这样用户只能输入整数/浮点数/什么?特别是,有没有办法将贴纸过滤到文本字段?在Java中,我使用了DocumentFilter来做到这一点。我尝试了一些变体:
object inputField extends TextField{
peer.getDocument.asInstanceOf[AbstractDocument].setDocumentFilter(new DocumentFilter{
def insertString(fb: FilterBypass, offs: Integer, str: String, a: AttributeSet){
if(str.forall((c)=>c.isDigit)) super.insertString(fb, offs, str, a)
}
def replace(fb: FilterBypass, offs: Integer, l: Integer, str: String, a: AttributeSet){
if(str.forall((c)=>c.isDigit)) super.replace(fb, offs, l, str, a)
}
})
}
哪个不行。我做错了,还是Scala忽略了文档过滤器?还有另一种方法吗?我可能会使用完全java.swing的GUI,如果这就是它。
答案 0 :(得分:2)
您可以使用以下反应来实现此目的:
import swing._
import swing.event._
object SwingApp extends SimpleSwingApplication {
def top = new MainFrame {
contents = new TextField {
listenTo(keys)
reactions += { case e: KeyTyped =>
if (!e.char.isDigit) e.consume
}
}
}
}
<强>更新强>: 哦,我同意,这只适用于相对微不足道的案件。我发现你的原始解决方案有问题:你需要使用Ints所需的Integers,所以你的方法只是新方法,而不是抽象类方法的实现。以下是它对我有用的方法:
contents = new TextField {
object IntegralFilter extends DocumentFilter {
override def insertString(fb: FilterBypass, offs: Int, str: String, a: AttributeSet){
if(str.forall((c)=>c.isDigit)) super.insertString(fb, offs, str, a)
}
override def replace(fb: FilterBypass, offs: Int, l: Int, str: String, a: AttributeSet){
if(str.forall((c)=>c.isDigit)) super.replace(fb, offs, l, str, a)
}
}
peer.getDocument().asInstanceOf[AbstractDocument].setDocumentFilter(IntegralFilter)
}
注意使用“覆盖”。这就是我如何得到编译器错误和相应的IDE提示,如果我真的想用这个覆盖一些东西,我必须改变签名。
答案 1 :(得分:0)
这是正确处理除指数之外的所有有效数字的类:
class NumberField(initialValue: Double) extends TextField(initialValue.toString) {
// Note: exponents are not allowed
val numberFormatException = new NumberFormatException
listenTo(keys)
reactions += {
case event: KeyTyped => {
try {
// Don't allow "d" or "f" in the string even though it parses, e.g. 3.5d
if (event.char.isLetter)
throw numberFormatException
// Don't allow string that doesn't parse to a double
(text.substring(0, caret.position) +
event.char +
text.substring(caret.position)).toDouble
} catch {
case exception: NumberFormatException => event.consume
}
}
}
def value : Double = text.toDouble
}