2015-05-26 8 views
7

Ich bekomme eine Ausnahme und verstehe nicht, was es verursacht. Es ist eine FX-App mit FXML-Dateien. Am init() - Teil der App füge ich einen Listener zu einem Textfeld hinzu, das eine Funktion aufruft, die den String mit einer Regex für ein Muster überwacht.JavaFX Textfield mit Listener gibt: "java.lang.IllegalArgumentException: Der Start muss <= das Ende sein"

tf.textProperty().addListener(
     (observable, oldValue, newValue) -> { 
      handleInput(newValue); 
     }); 

die Funktion:

private void handleInput(String s) { 

      s = s.toUpperCase(); 
      Matcher matcher = Pattern 
        .compile(
          "^[A-Z]{2}(20|21|22|23|[0-1]\\d)[0-5]\\d(20|21|22|23|[0-1]\\d)[0-5]\\d(T\\s|C\\s|TC|CT|\\s\\s)$") 
        .matcher(s); 

      if (matcher.find()) { 

        // do something 

        // then clear the textfield 
        tf.clear(); 

       } else { 
        // do something else 
       } 
      } 

Es funktioniert aber gibt mir eine Ausnahme bei der Matcher übereinstimmt.

Die Ausnahme:

Exception in thread "JavaFX Application Thread" java.lang.IllegalArgumentException: The start must be <= the end 
    at javafx.scene.control.TextInputControl.getText(Unknown Source) 
    at javafx.scene.control.TextInputControl.updateContent(Unknown Source) 
    at javafx.scene.control.TextInputControl.replaceText(Unknown Source) 
    at com.sun.javafx.scene.control.skin.TextFieldSkin.replaceText(Unknown Source) 
    at com.sun.javafx.scene.control.behavior.TextFieldBehavior.replaceText(Unknown Source) 
    at com.sun.javafx.scene.control.behavior.TextInputControlBehavior.defaultKeyTyped(Unknown Source) 
    at com.sun.javafx.scene.control.behavior.TextInputControlBehavior.callAction(Unknown Source) 
    at com.sun.javafx.scene.control.behavior.BehaviorBase.callActionForEvent(Unknown Source) 
    at com.sun.javafx.scene.control.behavior.TextInputControlBehavior.callActionForEvent(Unknown Source) 
    at com.sun.javafx.scene.control.behavior.BehaviorBase.lambda$new$75(Unknown Source) 
    at com.sun.javafx.scene.control.behavior.BehaviorBase$$Lambda$88/1978656397.handle(Unknown Source) 
    at com.sun.javafx.event.CompositeEventHandler$NormalEventHandlerRecord.handleBubblingEvent(Unknown Source) 
    at com.sun.javafx.event.CompositeEventHandler.dispatchBubblingEvent(Unknown Source) 
    at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(Unknown Source) 
    at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(Unknown Source) 
    at com.sun.javafx.event.CompositeEventDispatcher.dispatchBubblingEvent(Unknown Source) 
    at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(Unknown Source) 
    at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(Unknown Source) 
    at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(Unknown Source) 
    at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(Unknown Source) 
    at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(Unknown Source) 
    at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(Unknown Source) 
    at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(Unknown Source) 
    at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(Unknown Source) 
    at com.sun.javafx.event.EventUtil.fireEventImpl(Unknown Source) 
    at com.sun.javafx.event.EventUtil.fireEvent(Unknown Source) 
    at javafx.event.Event.fireEvent(Unknown Source) 
    at javafx.scene.Scene$KeyHandler.process(Unknown Source) 
    at javafx.scene.Scene$KeyHandler.access$1800(Unknown Source) 
    at javafx.scene.Scene.impl_processKeyEvent(Unknown Source) 
    at javafx.scene.Scene$ScenePeerListener.keyEvent(Unknown Source) 
    at com.sun.javafx.tk.quantum.GlassViewEventHandler$KeyEventNotification.run(Unknown Source) 
    at com.sun.javafx.tk.quantum.GlassViewEventHandler$KeyEventNotification.run(Unknown Source) 
    at java.security.AccessController.doPrivileged(Native Method) 
    at com.sun.javafx.tk.quantum.GlassViewEventHandler.lambda$handleKeyEvent$349(Unknown Source) 
    at com.sun.javafx.tk.quantum.GlassViewEventHandler$$Lambda$349/1135388943.get(Unknown Source) 
    at com.sun.javafx.tk.quantum.QuantumToolkit.runWithoutRenderLock(Unknown Source) 
    at com.sun.javafx.tk.quantum.GlassViewEventHandler.handleKeyEvent(Unknown Source) 
    at com.sun.glass.ui.View.handleKeyEvent(Unknown Source) 
    at com.sun.glass.ui.View.notifyKey(Unknown Source) 
    at com.sun.glass.ui.win.WinApplication._runLoop(Native Method) 
    at com.sun.glass.ui.win.WinApplication.lambda$null$145(Unknown Source) 
    at com.sun.glass.ui.win.WinApplication$$Lambda$36/2117255219.run(Unknown Source) 
    at java.lang.Thread.run(Unknown Source)} 

ich einige Vorschläge bereits versucht, die ich hier in anderen Einträge gefunden, wie die Sehne zu überprüfen, bevor es an die Matcher geben:

if (!tf.getText() == null) { 

oder

if (!tf.getText().equals("") { 

aber die Ausnahme bleibt. Wenn ich entferne:

tf.clear(); 

alles funktioniert gut.

... irgendwelche ideen jemand?

EDIT swinkler Lösung:

die Ausnahme mit Quellen i erhalten, wenn swinkler des Code - JDK 1.8.0_45:

Exception in thread "JavaFX Application Thread" java.lang.IllegalArgumentException: The start must be <= the end 
    at javafx.scene.control.TextInputControl.getText(TextInputControl.java:446) 
    at javafx.scene.control.TextInputControl.updateContent(TextInputControl.java:564) 
    at javafx.scene.control.TextInputControl.replaceText(TextInputControl.java:548) 
    at com.sun.javafx.scene.control.skin.TextFieldSkin.replaceText(TextFieldSkin.java:576) 
    at com.sun.javafx.scene.control.behavior.TextFieldBehavior.replaceText(TextFieldBehavior.java:202) 
    at com.sun.javafx.scene.control.behavior.TextInputControlBehavior.defaultKeyTyped(TextInputControlBehavior.java:238) 
    at com.sun.javafx.scene.control.behavior.TextInputControlBehavior.callAction(TextInputControlBehavior.java:139) 
    at com.sun.javafx.scene.control.behavior.BehaviorBase.callActionForEvent(BehaviorBase.java:218) 
    at com.sun.javafx.scene.control.behavior.TextInputControlBehavior.callActionForEvent(TextInputControlBehavior.java:127) 
    at com.sun.javafx.scene.control.behavior.BehaviorBase.lambda$new$75(BehaviorBase.java:135) 
    at com.sun.javafx.scene.control.behavior.BehaviorBase$$Lambda$91/476337053.handle(Unknown Source) 
    at com.sun.javafx.event.CompositeEventHandler$NormalEventHandlerRecord.handleBubblingEvent(CompositeEventHandler.java:218) 
    at com.sun.javafx.event.CompositeEventHandler.dispatchBubblingEvent(CompositeEventHandler.java:80) 
    at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:238) 
    at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:191) 
    at com.sun.javafx.event.CompositeEventDispatcher.dispatchBubblingEvent(CompositeEventDispatcher.java:59) 
    at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:58) 
    at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114) 
    at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:56) 
    at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114) 
    at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:56) 
    at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114) 
    at com.sun.javafx.event.EventUtil.fireEventImpl(EventUtil.java:74) 
    at com.sun.javafx.event.EventUtil.fireEvent(EventUtil.java:54) 
    at javafx.event.Event.fireEvent(Event.java:198) 
    at javafx.scene.Scene$KeyHandler.process(Scene.java:3965) 
    at javafx.scene.Scene$KeyHandler.access$1800(Scene.java:3911) 
    at javafx.scene.Scene.impl_processKeyEvent(Scene.java:2040) 
    at javafx.scene.Scene$ScenePeerListener.keyEvent(Scene.java:2502) 
    at com.sun.javafx.tk.quantum.GlassViewEventHandler$KeyEventNotification.run(GlassViewEventHandler.java:197) 
    at com.sun.javafx.tk.quantum.GlassViewEventHandler$KeyEventNotification.run(GlassViewEventHandler.java:147) 
    at java.security.AccessController.doPrivileged(Native Method) 
    at com.sun.javafx.tk.quantum.GlassViewEventHandler.lambda$handleKeyEvent$349(GlassViewEventHandler.java:228) 
    at com.sun.javafx.tk.quantum.GlassViewEventHandler$$Lambda$142/181559839.get(Unknown Source) 
    at com.sun.javafx.tk.quantum.QuantumToolkit.runWithoutRenderLock(QuantumToolkit.java:404) 
    at com.sun.javafx.tk.quantum.GlassViewEventHandler.handleKeyEvent(GlassViewEventHandler.java:227) 
    at com.sun.glass.ui.View.handleKeyEvent(View.java:546) 
    at com.sun.glass.ui.View.notifyKey(View.java:956) 
    at com.sun.glass.ui.win.WinApplication._runLoop(Native Method) 
    at com.sun.glass.ui.win.WinApplication.lambda$null$145(WinApplication.java:101) 
    at com.sun.glass.ui.win.WinApplication$$Lambda$36/2117255219.run(Unknown Source) 
    at java.lang.Thread.run(Thread.java:745) 
+0

Scheint, wie Sie einen Listener hinzufügen, denn wenn die Textproperty() des Textfeldes ändert. Wenn Sie ändern wollen, was der Text während der Behandlung des Ereignisses haben soll, sollten Sie es mit dem Parameter 'new value' machen anstelle von' clear() ' –

+0

Ich möchte das Textfeld für eine neue Eingabe bereit haben, sobald die Zeichenfolge es hat stimmte mit dem Muster überein. Ich habe auch versucht, tf.settext ("") anstelle von tf.clear() zu verwenden. Es gibt auch die gleiche Ausnahme. – VictorRomeo

+0

Der Punkt ist, sollten Sie nicht versuchen, den Text in dem Feld zu ändern, weil Sie in der Mitte der Handhabung des 'textmodified' Ereignisses sind. Ich denke, der richtige Weg ist, den Parameter 'newValue' auf" "zu stellen. –

Antwort

0

ich nicht deinen Fehler erhalten kann, wenn diese in einem einfachen JavaFX mit Anwendung. Hier ist der Code, mit dem ich Ihre Implementierung getestet habe. Meine Testeingabe ist "AA20552055T", um mit der Regexp übereinzustimmen - das Textfeld wird gelöscht.

Können Sie bitte mit Ihrer Lösung vergleichen:

public class JavaFXApplication1 extends Application { 

    @Override 
    public void start(Stage stage) throws Exception { 
     Parent root = FXMLLoader.load(getClass().getResource("FXMLDocument.fxml")); 
     Scene scene = new Scene(root); 
     stage.setScene(scene); 
     stage.show(); 
    } 

    public static void main(String[] args) { 
     launch(args); 
    } 

} 

Die Controller-Klasse mit Ihrer Logik:

public class FXMLDocumentController implements Initializable { 

    @FXML 
    private TextField textfield; 

    @Override 
    public void initialize(URL url, ResourceBundle rb) { 
     textfield.textProperty().addListener(
       (observable, oldValue, newValue) -> { 
        handleInput(newValue); 
       }); 
    } 

    private void handleInput(String s) { 

     s = s.toUpperCase(); 
     Matcher matcher = Pattern 
       .compile(
         "^[A-Z]{2}(20|21|22|23|[0-1]\\d)[0-5]\\d(20|21|22|23|[0-1]\\d)[0-5]\\d(T\\s|C\\s|TC|CT|\\s\\s)$") 
       .matcher(s); 

     if (matcher.find()) { 

        // do something 
        // then clear the textfield 
      textfield.clear(); 

     } else { 
      // do something else 
     } 
    } 
} 

Die FXML Datei:

<?xml version="1.0" encoding="UTF-8"?> 

<?import java.lang.*?> 
<?import java.util.*?> 
<?import javafx.scene.*?> 
<?import javafx.scene.control.*?> 
<?import javafx.scene.layout.*?> 

<AnchorPane id="AnchorPane" prefHeight="200" prefWidth="320" xmlns:fx="http://javafx.com/fxml/1" fx:controller="javafxapplication1.FXMLDocumentController"> 
    <children> 
     <TextField layoutX="126" layoutY="150" fx:id="textfield" /> 
    </children> 
</AnchorPane> 

der Kommentar In Bezug auf installierte ich JDK 1.8.0_45 (vor 1.8.0_20) Unter Windows 7 x64arbeitenWieder kein Fehler.

Here is the jar Netbeans erstellt automatisch - ich habe es von CMD getestet. Funktioniert auch gut. Können Sie testen, ob die von CMD ausgeführte JAR-Datei auf Ihrem Computer einwandfrei funktioniert?

Zum Debuggen - das ist die Methode, bei der die Ausnahmedaten durch den Parameter angegeben werden. Änderung hat eine start und end.

private void updateContent(TextFormatter.Change change, boolean forceNewUndoRecord) { 
     final boolean nonEmptySelection = getSelection().getLength() > 0; 
     String oldText = getText(change.start, change.end); 

Die Anfangs- und Endwerte dann lösen die Ausnahme in getText(...):

public String getText(int start, int end) { 
     if (start > end) { 
      throw new IllegalArgumentException("The start must be <= the end"); 
     } 

     if (start < 0 
      || end > getLength()) { 
      throw new IndexOutOfBoundsException(); 
     } 

     return getContent().get(start, end); 
    } 
+0

Danke für das Beispiel. Ich habe einen Ausschneiden und Einfügen und bekomme den gleichen Fehler (dieses Mal mit Quellen, unten veröffentlicht. Ich habe vergessen, Initialisierbar * ooops * - Zeit, um eine Pause zu machen implementieren.) - BTW. Ich verwende JDK 1.8.0_45 – VictorRomeo

+0

@VictorRomeo: Ich habe einige Umgebungsinformationen hinzugefügt. – swinkler

+0

danke - ich bekomme einen Fehler mit Ihrem .jar - Screenshot hier: http://up.picr.de//22049687bw.jpg - irgendwelche Ideen? – VictorRomeo

7

hatte ich die gleiche problem und fand den Bug-Report JDK-8081700, die das Problem gelöst. Es stellt sich heraus kein Fehler.

Der Testfall versucht, die Texteigenschaft innerhalb der Änderung Handler zu ändern. Dies wird nicht unterstützt, und die Property-Ereignishandler sind nicht einspringend.

Der richtige Weg ist für die Anwendung die Änderung zu verzögern, runLater mit():

if (matcher.find()) { 
     System.err.println("true"); 
     Platform.runLater(() -> { 
      textField.clear(); 
     }); 
    } 
Verwandte Themen