diff --git a/client/src/main/java/ru/trader/controllers/MissionsController.java b/client/src/main/java/ru/trader/controllers/MissionsController.java index b336232..29a10e9 100644 --- a/client/src/main/java/ru/trader/controllers/MissionsController.java +++ b/client/src/main/java/ru/trader/controllers/MissionsController.java @@ -7,10 +7,7 @@ import javafx.fxml.FXML; import javafx.scene.control.Button; import javafx.scene.control.ComboBox; import javafx.scene.control.TextField; -import ru.trader.model.ItemModel; -import ru.trader.model.MarketModel; -import ru.trader.model.MissionModel; -import ru.trader.model.StationModel; +import ru.trader.model.*; import ru.trader.view.support.NumberField; import ru.trader.view.support.autocomplete.AutoCompletion; import ru.trader.view.support.autocomplete.StationsProvider; @@ -56,9 +53,9 @@ public class MissionsController { private void initialize(){ MarketModel world = MainController.getWorld(); StationsProvider provider = new StationsProvider(world); - receiver = new AutoCompletion<>(receiverText, provider, provider.getConverter()); + receiver = new AutoCompletion<>(receiverText, provider, ModelFabric.NONE_STATION, provider.getConverter()); provider = new StationsProvider(world); - buyer = new AutoCompletion<>(buyerText, provider, provider.getConverter()); + buyer = new AutoCompletion<>(buyerText, provider, ModelFabric.NONE_STATION, provider.getConverter()); item.setItems(world.itemsProperty()); addCourierBtn.disableProperty().bind(Bindings.createBooleanBinding(() -> receiver.getCompletion() == null, receiver.completionProperty()) .or(courierProfit.wrongProperty()) diff --git a/client/src/main/java/ru/trader/controllers/ProfileController.java b/client/src/main/java/ru/trader/controllers/ProfileController.java index d18ad0f..24f8d3c 100644 --- a/client/src/main/java/ru/trader/controllers/ProfileController.java +++ b/client/src/main/java/ru/trader/controllers/ProfileController.java @@ -9,10 +9,7 @@ import javafx.scene.control.ComboBox; import javafx.scene.control.TextField; import javafx.util.StringConverter; import ru.trader.core.Engine; -import ru.trader.model.MarketModel; -import ru.trader.model.ProfileModel; -import ru.trader.model.StationModel; -import ru.trader.model.SystemModel; +import ru.trader.model.*; import ru.trader.view.support.NumberField; import ru.trader.view.support.ViewUtils; import ru.trader.view.support.autocomplete.AutoCompletion; @@ -52,7 +49,7 @@ public class ProfileController { profile = MainController.getProfile(); MarketModel world = MainController.getWorld(); SystemsProvider provider = new SystemsProvider(world); - system = new AutoCompletion<>(systemText, provider, provider.getConverter()); + system = new AutoCompletion<>(systemText, provider, ModelFabric.NONE_SYSTEM, provider.getConverter()); engine.setItems(FXCollections.observableList(Engine.getEngines())); engine.setConverter(new EngineStringConverter()); btnAddSystem.setOnAction(e -> Screeners.showSystemsEditor(null)); @@ -71,9 +68,9 @@ public class ProfileController { }); system.completionProperty().addListener((ov, o , n) -> { if (!ignoreChanges){ + ignoreChanges = true; profile.setSystem(n); } - ignoreChanges = true; station.setItems(n.getStationsList()); ignoreChanges = false; }); @@ -142,7 +139,10 @@ public class ProfileController { private final ChangeListener nameListener = (ov, o, n) -> ViewUtils.doFX(() -> name.setText(n)); private final ChangeListener balanceListener = (ov, o, n) -> ViewUtils.doFX(() -> balance.setValue(n)); - private final ChangeListener systemListener = (ov, o, n) -> ViewUtils.doFX(() -> system.setValue(n)); + private final ChangeListener systemListener = (ov, o, n) -> { + if (!ignoreChanges) + ViewUtils.doFX(() -> system.setValue(n)); + }; private final ChangeListener stationListener = (ov, o, n) -> ViewUtils.doFX(() -> station.setValue(n)); private final ChangeListener massListener = (ov, o, n) -> ViewUtils.doFX(() -> mass.setValue(n)); private final ChangeListener tankListener = (ov, o, n) -> ViewUtils.doFX(() -> tank.setValue(n)); diff --git a/client/src/main/java/ru/trader/view/support/autocomplete/AutoCompletion.java b/client/src/main/java/ru/trader/view/support/autocomplete/AutoCompletion.java index 54b4465..7a6b218 100644 --- a/client/src/main/java/ru/trader/view/support/autocomplete/AutoCompletion.java +++ b/client/src/main/java/ru/trader/view/support/autocomplete/AutoCompletion.java @@ -2,22 +2,40 @@ package ru.trader.view.support.autocomplete; import javafx.beans.property.ObjectProperty; import javafx.beans.property.SimpleObjectProperty; +import javafx.beans.value.ChangeListener; import javafx.scene.control.TextField; import javafx.util.Callback; import javafx.util.StringConverter; import org.controlsfx.control.textfield.AutoCompletionBinding; -import org.controlsfx.control.textfield.TextFields; import java.util.Collection; public class AutoCompletion { + private static StringConverter defaultStringConverter() { + return new StringConverter() { + @Override public String toString(T t) { + return t == null ? null : t.toString(); + } + @SuppressWarnings("unchecked") + @Override public T fromString(String string) { + return (T) string; + } + }; + } + private final ObjectProperty completion = new SimpleObjectProperty<>(); private final StringConverter converter; - private final AutoCompletionBinding binding; + private final AutoTextFieldBinding binding; + private final T notFoundItem; - public AutoCompletion(final TextField textField, final Callback> suggestionProvider, final StringConverter converter) { + public AutoCompletion(final TextField textField, final Callback> suggestionProvider) { + this(textField, suggestionProvider, null, defaultStringConverter()); + } + + public AutoCompletion(final TextField textField, final Callback> suggestionProvider, T notFoundItem, final StringConverter converter) { this.converter = converter; - binding = TextFields.bindAutoCompletion(textField, suggestionProvider, converter); + this.notFoundItem = notFoundItem; + binding = new AutoTextFieldBinding(textField, suggestionProvider); binding.setOnAutoCompleted(e -> completion.setValue(e.getCompletion())); } @@ -29,6 +47,10 @@ public class AutoCompletion { return completion.get(); } + public TextField getCompletionTarget(){ + return binding.getCompletionTarget(); + } + public ObjectProperty completionProperty() { return completion; } @@ -39,6 +61,47 @@ public class AutoCompletion { public void setValue(T value) { completion.setValue(value); - ((TextField)binding.getCompletionTarget()).setText(converter.toString(value)); + binding.completeUserInput(value); + } + + private class AutoTextFieldBinding extends AutoCompletionBinding{ + public AutoTextFieldBinding(final TextField textField, + Callback> suggestionProvider) { + + super(textField, suggestionProvider, converter); + + getCompletionTarget().textProperty().addListener(textChangeListener); + getCompletionTarget().focusedProperty().addListener(focusChangedListener); + } + + /** {@inheritDoc} */ + @Override public TextField getCompletionTarget(){ + return (TextField)super.getCompletionTarget(); + } + + /** {@inheritDoc} */ + @Override public void dispose(){ + getCompletionTarget().textProperty().removeListener(textChangeListener); + getCompletionTarget().focusedProperty().removeListener(focusChangedListener); + } + + /** {@inheritDoc} */ + @Override protected void completeUserInput(T completion){ + String newText = converter.toString(completion); + getCompletionTarget().setText(newText); + getCompletionTarget().positionCaret(newText.length()); + } + + private final ChangeListener textChangeListener = (obs, oldText, newText) -> { + if (getCompletionTarget().isFocused()) { + setUserInput(newText); + completion.setValue(notFoundItem); + } + }; + + private final ChangeListener focusChangedListener = (obs, oldFocused, newFocused) -> { + if(newFocused == false) + hidePopup(); + }; } }