/**
* If the entry is a recurrence (see {@link #recurrenceProperty()}) then
* this property will store a reference to the entry for which the
* recurrence was created.
*
* @return the entry that was the source of the recurrence
*/
public final ReadOnlyObjectProperty<Entry<T>> recurrenceSourceProperty() {
if (recurrenceSource == null) {
recurrenceSource = new ReadOnlyObjectWrapper<Entry<T>>(this, "recurrenceSource") { //$NON-NLS-1$
@Override
public void set(Entry<T> newEntry) {
super.set(newEntry);
if (newEntry != null) {
setRecurrence(true);
} else {
setRecurrence(false);
}
}
};
}
return recurrenceSource.getReadOnlyProperty();
}
java类javafx.beans.property.ReadOnlyObjectProperty的实例源码
Entry.java 文件源码
项目:CalendarFX
阅读 65
收藏 0
点赞 0
评论 0
VirtualAssetEditorDialog.java 文件源码
项目:jmonkeybuilder
阅读 33
收藏 0
点赞 0
评论 0
@Override
@FXThread
protected @NotNull ObservableBooleanValue buildAdditionalDisableCondition() {
final VirtualResourceTree<C> resourceTree = getResourceTree();
final MultipleSelectionModel<TreeItem<VirtualResourceElement<?>>> selectionModel = resourceTree.getSelectionModel();
final ReadOnlyObjectProperty<TreeItem<VirtualResourceElement<?>>> selectedItemProperty = selectionModel.selectedItemProperty();
final Class<C> type = getObjectsType();
final BooleanBinding typeCondition = new BooleanBinding() {
@Override
protected boolean computeValue() {
final TreeItem<VirtualResourceElement<?>> treeItem = selectedItemProperty.get();
return treeItem == null || !type.isInstance(treeItem.getValue().getObject());
}
@Override
public Boolean getValue() {
return computeValue();
}
};
return Bindings.or(selectedItemProperty.isNull(), typeCondition);
}
RestNetworkService.java 文件源码
项目:Capstone2016
阅读 42
收藏 0
点赞 0
评论 0
@Override
public ReadOnlyObjectProperty<RequestStatus> loadCatchTypes(Consumer<CatchType> loadCallback) {
RestClient catchTypeClient = RestClient.create().method("GET").host("https://api.nestnz.org")
.path("/catch-type").connectTimeout(TIMEOUT);
return processReadRequest(ApiCatchType.class, catchTypeClient, apiCatchType -> {
URL imageUrl = null;
if (apiCatchType.getImageUrl() != null) {
try {
imageUrl = new URL(apiCatchType.getImageUrl());
} catch (MalformedURLException ex) {
LOG.log(Level.WARNING, "Error decoding image url: "+apiCatchType.getImageUrl(), ex);
}
}
CatchType catchType = new CatchType(apiCatchType.getId(), apiCatchType.getName(), imageUrl);
loadCallback.accept(catchType);
});
}
RestNetworkService.java 文件源码
项目:Capstone2016
阅读 34
收藏 0
点赞 0
评论 0
@Override
public ReadOnlyObjectProperty<RequestStatus> loadTrapline(Trapline trapline, Consumer<Trap> loadCallback) {
RestClient trapsClient = RestClient.create().method("GET").host("https://api.nestnz.org")
.path("/trap").connectTimeout(TIMEOUT).queryParam("trapline-id", Integer.toString(trapline.getId()));
return processReadRequest(ApiTrap.class, trapsClient, apiTrap -> {
if (apiTrap.getTraplineId() != trapline.getId()) {
LOG.log(Level.WARNING, apiTrap+" was returned in a request for trapline "+trapline.getId());
return;
}
LocalDateTime created = LocalDateTime.parse(apiTrap.getCreated().replace(' ', 'T'));
LocalDateTime lastReset = apiTrap.getLastReset() == null ? null : LocalDateTime.parse(apiTrap.getLastReset().replace(' ', 'T'));
Trap trap = new Trap(apiTrap.getId(), apiTrap.getNumber(),
apiTrap.getLatitude(), apiTrap.getLongitude(), TrapStatus.ACTIVE, created, lastReset);
loadCallback.accept(trap);
});
}
ListViewSelectionModelSelectItemsAccessor.java 文件源码
项目:reduxfx
阅读 30
收藏 0
点赞 0
评论 0
@SuppressWarnings("unchecked")
@Override
public void set(Consumer<Object> dispatcher, Object node, String name, VProperty vProperty) {
if(! (node instanceof ListView)) {
throw new IllegalStateException("Trying to set selectionModel of node " + node);
}
final ListView listView = (ListView) node;
final ReadOnlyObjectProperty selectedItemProperty = listView.getSelectionModel().selectedItemProperty();
clearListeners(node, selectedItemProperty);
final Object value = vProperty.isValueDefined()? vProperty.getValue() : null;
listView.getSelectionModel().select(value);
if(vProperty.getChangeListener().isDefined()) {
setChangeListener(dispatcher, node, selectedItemProperty, vProperty.getChangeListener().get());
}
if(vProperty.getInvalidationListener().isDefined()) {
setInvalidationListener(dispatcher, node, selectedItemProperty, vProperty.getInvalidationListener().get());
}
}
MplIdeController.java 文件源码
项目:MPL
阅读 32
收藏 0
点赞 0
评论 0
@Override
public FindReplaceDialog getFindReplaceDialog() {
if (findReplaceDialog == null) {
findReplaceDialog = new FindReplaceDialog(getWindow(), this);
ChangeListener<Node> focusOwnerListener = (observable, oldValue,
newValue) -> findReplaceDialog.getController().setFocusOwner(newValue);
ChangeListener<Scene> sceneListener = (observable, oldValue, newValue) -> {
if (oldValue != null)
oldValue.focusOwnerProperty().removeListener(focusOwnerListener);
if (newValue != null)
newValue.focusOwnerProperty().addListener(focusOwnerListener);
};
ReadOnlyObjectProperty<Scene> sceneProperty = root.sceneProperty();
sceneProperty.addListener(sceneListener);
sceneListener.changed(sceneProperty, null, sceneProperty.get());
}
return findReplaceDialog;
}
CompositeObservableBounds.java 文件源码
项目:j.commons
阅读 34
收藏 0
点赞 0
评论 0
private void invalidate() {
boolean initialized = false;
for (ReadOnlyObjectProperty<Bounds> property : sourceBounds) {
Bounds bounds = property.get();
if (!initialized) {
minX.set(floorIfNeeded(bounds.getMinX()));
minY.set(floorIfNeeded(bounds.getMinY()));
minZ.set(floorIfNeeded(bounds.getMinZ()));
maxX.set(ceilIfNeeded(bounds.getMaxX()));
maxY.set(ceilIfNeeded(bounds.getMaxY()));
maxZ.set(ceilIfNeeded(bounds.getMaxZ()));
initialized = true;
} else {
minX.set(Double.min(minX.get(), floorIfNeeded(bounds.getMinX())));
minY.set(Double.min(minY.get(), floorIfNeeded(bounds.getMinY())));
minZ.set(Double.min(minZ.get(), floorIfNeeded(bounds.getMinZ())));
maxX.set(Double.max(maxX.get(), ceilIfNeeded(bounds.getMaxX())));
maxY.set(Double.max(maxY.get(), ceilIfNeeded(bounds.getMaxY())));
maxZ.set(Double.max(maxZ.get(), ceilIfNeeded(bounds.getMaxZ())));
}
}
}
TournamentModuleEditorDialog.java 文件源码
项目:Tourney
阅读 32
收藏 0
点赞 0
评论 0
private void bindPossibleScoringButtons() {
ReadOnlyIntegerProperty selectedIndex = this.tablePossibleScores
.getSelectionModel().selectedIndexProperty();
ReadOnlyObjectProperty<PossibleScoring> selectedItem = this.tablePossibleScores
.getSelectionModel().selectedItemProperty();
// only enable move-up button if an item other than the topmost is
// selected
this.buttonMoveScoreUp.disableProperty().bind(
selectedIndex.isEqualTo(0).or(selectedItem.isNull()));
// only enable move-down button if an item other than the last one is
// selected
// index < size - 1 && selected != null
this.buttonMoveScoreDown.disableProperty().bind(
selectedIndex.greaterThanOrEqualTo(
Bindings.size(this.tablePossibleScores.getItems())
.subtract(1)).or(selectedItem.isNull()));
// only enable remove button if an item is selected
this.buttonRemoveScore.disableProperty().bind(selectedItem.isNull());
// only enable edit button if an item is selected
this.buttonEditScore.disableProperty().bind(selectedItem.isNull());
}
CSSFXMonitor.java 文件源码
项目:cssfx
阅读 37
收藏 0
点赞 0
评论 0
private void monitorStageScene(ReadOnlyObjectProperty<Scene> stageSceneProperty) {
// first listen to changes
stageSceneProperty.addListener(new ChangeListener<Scene>() {
@Override
public void changed(ObservableValue<? extends Scene> ov, Scene o, Scene n) {
if (o != null) {
unregisterScene(o);
}
if (n != null) {
registerScene(n);
}
}
});
if (stageSceneProperty.getValue() != null) {
registerScene(stageSceneProperty.getValue());
}
}
ContextMenuUtil.java 文件源码
项目:honest-profiler
阅读 31
收藏 0
点赞 0
评论 0
/**
* Helper method which provides extra logic for extracting the {@link TreeItem} {@link Property} from a
* {@link TreeTableCell}, which itself has no {@link TreeItem} property. The {@link TreeItem} {@link Property} we
* want to bind can be found in the containing {@link TreeTableRow} instead.
* <p>
*
* @param <T> the type of the item contained in the {@link TreeTableRow}
* @param appCtx the {@link ApplicationContext} of the application
* @param ctxMenuProperty the {@link ContextMenu} {@link Property} of the {@link TreeTableCell}
* @param tableRowProperty the {@link TreeTableRow} {@link Property} of the {@link TreeTableCell}
*/
private static <T> void bindContextMenuForTreeTableCell(ApplicationContext appCtx,
ObjectProperty<ContextMenu> ctxMenuProperty,
ReadOnlyObjectProperty<TreeTableRow<T>> tableRowProperty)
{
tableRowProperty.addListener((property, oldValue, newValue) ->
{
// If the containing TreeTableRow disappears, unbind the context menu if any
if (newValue == null)
{
ctxMenuProperty.unbind();
return;
}
// Otherwise, bind the ContextMenu to the TreeItem Property of the containing TreeTable row.
bindContextMenu(appCtx, ctxMenuProperty, newValue.treeItemProperty());
});
}
TabService.java 文件源码
项目:AsciidocFX
阅读 28
收藏 0
点赞 0
评论 0
public void initializeTabChangeListener(TabPane tabPane) {
ReadOnlyObjectProperty<Tab> itemProperty = tabPane.getSelectionModel().selectedItemProperty();
tabPane.setOnMouseReleased(event -> {
Optional.ofNullable(itemProperty)
.map(ObservableObjectValue::get)
.filter(e -> e instanceof MyTab)
.map(e -> (MyTab) e)
.map(MyTab::getEditorPane)
.ifPresent(EditorPane::focus);
});
itemProperty.addListener((observable, oldValue, selectedTab) -> {
Optional.ofNullable(selectedTab)
.filter(e -> e instanceof MyTab)
.map(e -> (MyTab) e)
.map(MyTab::getEditorPane)
.filter(EditorPane::getReady)
.ifPresent(EditorPane::updatePreviewUrl);
});
}
SlidePane.java 文件源码
项目:AsciidocFX
阅读 22
收藏 0
点赞 0
评论 0
@PostConstruct
public void afterInit() {
threadService.runActionLater(() -> {
getWindow().setMember("afx", controller);
ReadOnlyObjectProperty<Worker.State> stateProperty = webEngine().getLoadWorker().stateProperty();
WebView popupView = new WebView();
Stage stage = new Stage();
stage.setScene(new Scene(popupView));
stage.setTitle("AsciidocFX");
InputStream logoStream = SlidePane.class.getResourceAsStream("/logo.png");
stage.getIcons().add(new Image(logoStream));
webEngine().setCreatePopupHandler(param -> {
if (!stage.isShowing()) {
stage.show();
popupView.requestFocus();
}
return popupView.getEngine();
});
stateProperty.addListener(this::stateListener);
});
}
ZoomableCanvas.java 文件源码
项目:afc
阅读 43
收藏 0
点赞 0
评论 0
@Override
public ReadOnlyObjectProperty<Rectangle2afp<?, ?, ?, ?, ?, ?>> viewportBoundsProperty() {
if (this.viewportBounds == null) {
this.viewportBounds = new ReadOnlyObjectWrapper<>(this, VIEWPORT_BOUNDS_PROPERTY);
this.viewportBounds.bind(Bindings.createObjectBinding(() -> {
final double scale = getScaleValue();
final double visibleAreaWidth = getWidth() / scale;
final double visibleAreaHeight = getHeight() / scale;
final double visibleAreaX = getViewportCenterX() - visibleAreaWidth / 2.;
final double visibleAreaY = getViewportCenterY() - visibleAreaHeight / 2.;
return new Rectangle2d(visibleAreaX, visibleAreaY, visibleAreaWidth, visibleAreaHeight);
}, widthProperty(), heightProperty(), viewportCenterXProperty(), viewportCenterYProperty(),
scaleValueProperty()));
}
return this.viewportBounds.getReadOnlyProperty();
}
EntryViewBase.java 文件源码
项目:CalendarFX
阅读 44
收藏 0
点赞 0
评论 0
/**
* The date control where the entry view is shown.
*
* @return the date control
*/
public final ReadOnlyObjectProperty<T> dateControlProperty() {
if (dateControl == null) {
dateControl = new ReadOnlyObjectWrapper<>(this, "dateControl", _dateControl); //$NON-NLS-1$
}
return dateControl.getReadOnlyProperty();
}
EntryViewBase.java 文件源码
项目:CalendarFX
阅读 33
收藏 0
点赞 0
评论 0
/**
* The time where the entry view starts (not the start time of the calendar
* entry).
*
* @return the start time of the view (not of the calendar entry)
*/
public final ReadOnlyObjectProperty<LocalTime> startTimeProperty() {
if (startTime == null) {
startTime = new ReadOnlyObjectWrapper<>(this, "startTime", _startTime); //$NON-NLS-1$
}
return startTime.getReadOnlyProperty();
}
EntryViewBase.java 文件源码
项目:CalendarFX
阅读 37
收藏 0
点赞 0
评论 0
/**
* The time where the entry view ends (not the end time of the calendar
* entry).
*
* @return the end time of the view (not of the calendar entry)
*/
public final ReadOnlyObjectProperty<LocalTime> endTimeProperty() {
if (endTime == null) {
endTime = new ReadOnlyObjectWrapper<>(this, "endTime", _endTime); //$NON-NLS-1$
}
return endTime.getReadOnlyProperty();
}
Entry.java 文件源码
项目:CalendarFX
阅读 33
收藏 0
点赞 0
评论 0
/**
* The property used to store the end time of the recurrence rule.
*
* @return the recurrence rule end time
* @see #recurrenceRuleProperty()
*/
public final ReadOnlyObjectProperty<LocalDate> recurrenceEndProperty() {
if (recurrenceEnd == null) {
recurrenceEnd = new ReadOnlyObjectWrapper<>(this, "recurrenceEnd", _recurrenceEnd); //$NON-NLS-1$
}
return recurrenceEnd.getReadOnlyProperty();
}
Entry.java 文件源码
项目:CalendarFX
阅读 42
收藏 0
点赞 0
评论 0
/**
* A property used to store a time zone for the entry. The time zone is
* needed for properly interpreting the dates and times of the entry.
*
* @return the time zone property
*/
public final ReadOnlyObjectProperty<ZoneId> zoneIdProperty() {
if (zoneId == null) {
zoneId = new ReadOnlyObjectWrapper<>(this, "zoneId", getInterval().getZoneId()); //$NON-NLS-1$
}
return zoneId.getReadOnlyProperty();
}
Entry.java 文件源码
项目:CalendarFX
阅读 28
收藏 0
点赞 0
评论 0
/**
* A read-only property used for retrieving the end date of the entry. The
* property gets updated whenever the end date inside the entry interval
* changes (see {@link #intervalProperty()}).
*
* @return the end date of the entry
*/
public final ReadOnlyObjectProperty<LocalDate> endDateProperty() {
if (endDate == null) {
endDate = new ReadOnlyObjectWrapper<>(this, "endDate", getInterval().getEndDate()); //$NON-NLS-1$
}
return endDate.getReadOnlyProperty();
}
Entry.java 文件源码
项目:CalendarFX
阅读 43
收藏 0
点赞 0
评论 0
/**
* A read-only property used for retrieving the end time of the entry. The
* property gets updated whenever the end time inside the entry interval
* changes (see {@link #intervalProperty()}).
*
* @return the end time of the entry
*/
public final ReadOnlyObjectProperty<LocalTime> endTimeProperty() {
if (endTime == null) {
endTime = new ReadOnlyObjectWrapper<>(this, "endTime", getInterval().getEndTime()); //$NON-NLS-1$
}
return endTime.getReadOnlyProperty();
}
ConstraintSpecificationValidator.java 文件源码
项目:stvs
阅读 38
收藏 0
点赞 0
评论 0
/**
* <p>
* Creates a validator with given observable models as context information.
* </p>
*
* <p>
* The validator observes changes in any of the given context models. It automatically updates the
* validated specification (see {@link #validSpecificationProperty()}) and/or the problems with
* the constraint specification (see {@link #problemsProperty()}).
* </p>
*
* @param typeContext the extracted types (esp. enums) from the code area
* @param codeIoVariables the extracted {@link CodeIoVariable}s from the code area
* @param validFreeVariables the most latest validated free variables from the
* {@link FreeVariableList}.
* @param specification the specification to be validated
*/
public ConstraintSpecificationValidator(ObjectProperty<List<Type>> typeContext,
ObjectProperty<List<CodeIoVariable>> codeIoVariables,
ReadOnlyObjectProperty<List<ValidFreeVariable>> validFreeVariables,
ConstraintSpecification specification) {
this.typeContext = typeContext;
this.codeIoVariables = codeIoVariables;
this.validFreeVariables = validFreeVariables;
this.specification = specification;
this.problems = new SimpleObjectProperty<>(new ArrayList<>());
this.validSpecification = new NullableProperty<>();
this.valid = new SimpleBooleanProperty(false);
// All these ObservableLists invoke the InvalidationListeners on deep updates
// So if only a cell in the Specification changes, the change listener on the ObservableList
// two layers above gets notified.
specification.getRows().addListener(listenToSpecUpdate);
specification.getDurations().addListener(listenToSpecUpdate);
specification.getColumnHeaders().addListener(listenToSpecUpdate);
typeContext.addListener(listenToSpecUpdate);
codeIoVariables.addListener(listenToSpecUpdate);
validFreeVariables.addListener(listenToSpecUpdate);
recalculateSpecProblems();
}
AssetEditorDialog.java 文件源码
项目:jmonkeybuilder
阅读 34
收藏 0
点赞 0
评论 0
@Override
@FXThread
protected @NotNull ObservableBooleanValue buildAdditionalDisableCondition() {
final ResourceTree resourceTree = getResourceTree();
final MultipleSelectionModel<TreeItem<ResourceElement>> selectionModel = resourceTree.getSelectionModel();
final ReadOnlyObjectProperty<TreeItem<ResourceElement>> selectedItemProperty = selectionModel.selectedItemProperty();
return selectedItemProperty.isNull();
}
ParticlesAssetEditorDialog.java 文件源码
项目:jmonkeybuilder
阅读 44
收藏 0
点赞 0
评论 0
@Override
@FXThread
protected @NotNull ObservableBooleanValue buildAdditionalDisableCondition() {
final ComboBox<String> comboBox = getTextureParamNameComboBox();
final SingleSelectionModel<String> selectionModel = comboBox.getSelectionModel();
final ReadOnlyObjectProperty<String> itemProperty = selectionModel.selectedItemProperty();
final ObservableBooleanValue parent = super.buildAdditionalDisableCondition();
return Bindings.and(parent, itemProperty.isNull().or(itemProperty.isEqualTo("")));
}
DockTab.java 文件源码
项目:Gargoyle
阅读 37
收藏 0
点赞 0
评论 0
private static ReadOnlyObjectProperty<? extends Control> getControlProperty(Object obj) {
if (obj instanceof TableColumn) {
return ((TableColumn) obj).tableViewProperty();
} else if (obj instanceof TreeTableColumn) {
return ((TreeTableColumn) obj).treeTableViewProperty();
} else if (obj instanceof DockTab) {
return ((DockTab) obj).tabPaneProperty();
}
return null;
}
DummyService.java 文件源码
项目:javaone2016
阅读 36
收藏 0
点赞 0
评论 0
@Override
public ReadOnlyObjectProperty<EnabledOTNExperiences> retrieveEnabledOTNExperiences() {
if (enabledOTNExperiences == null) {
EnabledOTNExperiences otnExperiences = new EnabledOTNExperiences();
otnExperiences.badgeEnabledProperty().set(true);
otnExperiences.coffeeEnabledProperty().set(true);
otnExperiences.embroiderEnabledProperty().set(true);
otnExperiences.gameEnabledProperty().set(true);
otnExperiences.vote3dEnabledProperty().set(true);
otnExperiences.iotworkshopEnabledProperty().set(true);
enabledOTNExperiences = new ReadOnlyObjectWrapper<>(otnExperiences);
}
return enabledOTNExperiences.getReadOnlyProperty();
}
CloudLinkService.java 文件源码
项目:javaone2016
阅读 40
收藏 0
点赞 0
评论 0
@Override
public ReadOnlyObjectProperty<EnabledOTNExperiences> retrieveEnabledOTNExperiences() {
if (enabledOTNExperiences == null) {
enabledOTNExperiences = new ReadOnlyObjectWrapper<>();
GluonObservableObject<EnabledOTNExperiences> otnExperiences = DataProvider.retrieveObject(cloudGluonClient.createObjectDataReader("enabledOtnExperiences", EnabledOTNExperiences.class, SyncFlag.OBJECT_READ_THROUGH));
otnExperiences.initializedProperty().addListener((obs, ov, nv) -> {
if (nv) {
enabledOTNExperiences.setValue(otnExperiences.get());
}
});
}
return enabledOTNExperiences.getReadOnlyProperty();
}
CloudLinkService.java 文件源码
项目:javaone2016
阅读 42
收藏 0
点赞 0
评论 0
@Override
public ReadOnlyObjectProperty<LatestClearThreeDModelVotes> retrieveLatestClearVotes() {
if (latestClearVotes == null) {
latestClearVotes = new ReadOnlyObjectWrapper<>();
GluonObservableObject<LatestClearThreeDModelVotes> gluonLatestClearVotes = DataProvider.retrieveObject(cloudGluonClient.createObjectDataReader("latestClearThreeDModelVotes", LatestClearThreeDModelVotes.class, SyncFlag.OBJECT_READ_THROUGH));
gluonLatestClearVotes.initializedProperty().addListener((obs, ov, nv) -> {
if (nv) {
latestClearVotes.setValue(gluonLatestClearVotes.get());
}
});
}
return latestClearVotes.getReadOnlyProperty();
}
ColumnizersController.java 文件源码
项目:fx-log
阅读 37
收藏 0
点赞 0
评论 0
private void initializePatternsPane() {
ReadOnlyObjectProperty<Columnizer> selectedColumnizer = columnizersPane.selectedItemProperty();
selectedColumnizerPane.disableProperty().bind(selectedColumnizer.isNull());
ListBinding<Pattern> patterns = UIUtils.selectList(selectedColumnizer, Columnizer::getPatterns);
Predicate<String> isValidRegex = regex -> createPattern(regex) != null;
patternsPane.setItemFactory(ColumnizersController::createPattern);
patternsPane.setItemDuplicator(p -> p); // not updated anyway
patternsPane.setNewItemValidator(isValidRegex);
patternsPane.getList().setConverter(ColumnizersController::createPattern, Pattern::pattern, isValidRegex);
patternsPane.getList().itemsProperty().bind(patterns);
initializeColumnsTable();
}
LoginService.java 文件源码
项目:Capstone2016
阅读 54
收藏 0
点赞 0
评论 0
/**
* Tries to renew the {@link #sessionTokenProperty} using the username & password used in the last call to {@link #login(String, String)}.
* @return The {@link #loginStatusProperty()}, which can be listened to & indicates when the request has completed
* @throws IllegalStateException if no username & password have been saved for future use (i.e. if no successful call to {@link #login(String, String)} has completed before calling this method)
*/
public ReadOnlyObjectProperty<LoginStatus> renewSession () {
if (username == null || password == null) {
throw new IllegalStateException("Username & password not set!");
}
return login(username, password);
}
TraplineMonitorService.java 文件源码
项目:Capstone2016
阅读 59
收藏 0
点赞 0
评论 0
/**
* Sends logged catches to the server
* @return A {@link ReadOnlyObjectProperty} which is set to {@link RequestStatus#SUCCESS} if all catches were sent successfully, or to an error if any requests failed.
*/
public ReadOnlyObjectProperty<RequestStatus> sendCatchesToServer () {
ReadOnlyObjectWrapper<RequestStatus> status = new ReadOnlyObjectWrapper<>();
if (loggedCatches.isEmpty()) {
//Run the status update later, so the calling method has a chance to register a listener first
Platform.runLater(() -> status.set(RequestStatus.SUCCESS));
} else {
Platform.runLater(() -> status.set(RequestStatus.PENDING));
IntegerProperty remaining = new SimpleIntegerProperty(loggedCatches.size());
remaining.addListener((obs, oldVal, newVal) -> {
if (newVal.intValue() == 0) {
status.set(RequestStatus.SUCCESS);
}
});
for (Pair<Integer, Catch> c : loggedCatches) {
networkService.sendLoggedCatch(c.getKey(), c.getValue()).addListener((obs, oldStatus, newStatus) -> {
switch (newStatus) {
case PENDING:
break;
case SUCCESS:
remaining.set(remaining.get()-1);
loggedCatches.remove(c);
break;
case FAILED_OTHER:
LOG.log(Level.WARNING, "Failed to send logged catch "+c+" (server responded with an error code) - removing from cache.");
loggedCatches.remove(c);
trapline.getTrap(c.getKey()).getCatches().remove(c.getValue());
remaining.set(remaining.get()-1);
break;
case FAILED_NETWORK:
case FAILED_UNAUTHORISED:
status.set(newStatus);
break;
}
});
}
LOG.log(Level.INFO, "Sent "+loggedCatches.size()+" logged catches to the server.");
}
return status.getReadOnlyProperty();
}