JavaFXのTextAreaにおけるタブの制御方法に代替無し
問題
JavaFXのTextAreaにおいて、タブキーを押した場合にタブ文字を入れるのではなく、次のフィールドにフォーカスを写してほしいのだが、タブ文字として入力されてしまう。これを以下のように制御したい。
- タブのみの場合は次のフィールドへフォーカスを移す。
- CTRLと同時の場合にタブ文字を入力する。
- Shiftと同時の場合に前のフィールドにフォーカスを移す。
Java8での解決策とJava9の対応
/** これはJava8でコンパイルする */
import com.sun.javafx.scene.control.behavior.*;
import com.sun.javafx.scene.control.skin.*;
......
textArea.addEventFilter(KeyEvent.KEY_PRESSED, new EventHandler<KeyEvent>() {
@SuppressWarnings("restriction")
@Override
public void handle(KeyEvent event) {
if (event.getCode() != KeyCode.TAB) return;
if (!tabTraverse) return;
try {
TextAreaSkin skin = (TextAreaSkin)textArea.getSkin();
BehaviorBase<?> bb = skin.getBehavior();
if (!(bb instanceof TextAreaBehavior)) return;
TextAreaBehavior behavior = (TextAreaBehavior)bb;
if (event.isControlDown()) {
behavior.callAction("InsertTab");
} else if (event.isShiftDown()) {
behavior.callAction("TraversePrevious");
} else {
behavior.callAction("TraverseNext");
}
event.consume();
} catch (NoClassDefFoundError ex) {
// Java9でJavaFXの仕様変更。代替策なし
}
}
});
Java9で仕様変更されており、TextAreaSkinが正規のクラスとなったのは良いのだが、getBehavior()メソッドがなくなり、同じ動作をさせることができなくなってしまった。上のコードは、Java9での実行においては単純に何もしない。