JavaFX IndexOutOfBoundException: индекс -1 выходит за пределы для длины 2 (я получаю эту ошибку случайным образом в своеJAVA

Программисты JAVA общаются здесь
Ответить
Anonymous
 JavaFX IndexOutOfBoundException: индекс -1 выходит за пределы для длины 2 (я получаю эту ошибку случайным образом в свое

Сообщение Anonymous »

// вот мой метод инициализации и создания зон хранения, в которых у меня есть некоторые

// объявления эффектов мыши

// в этом коде я работаю над тремя изображениями, два из которых имеют эффект щелчка, сбрасывая изображение шара при щелчке по ним

//один код для колеса телеги, который также имеет эффект наведения и эффект щелчка

//все изображения имеют код set и сбросить и очистить

Код: Выделить всё

public void initialize(URL location,
ResourceBundle resources)  {

// Setup outcome buttons for multiple selection
setupOutcomeButtonsForMultipleSelection();

// Setup individual radio buttons as
independent selections
setupIndividualRadioButtons();
// Apply responsive scaling so dashboard
fits any window size
setupResponsiveScaling();

if (wagonWheelOverlay != null) {
wagonWheelOverlay.addEventFilter(javafx.scene.input.MouseEvent.ANY,
e -> {
synchronized (sceneGraphLock) {
if (isModifyingSceneGraph) e.consume();
}
});
}

if (pitchMapPane != null) {

pitchMapPane.addEventFilter(javafx.scene.input.MouseEvent.ANY,
e
-> {synchronized (sceneGraphLock) {
if (isModifyingSceneGraph) e.consume();
}
});
}
if (ballArrivalPane != null) {
ballArrivalPane.addEventFilter(javafx.scene.input.MouseEvent.ANY, e
-> { synchronized (sceneGraphLock) {
if (isModifyingSceneGraph) e.consume();
}
});
}

if (pitchMapPane != null) {
pitchMapPane.setUserData(null);
pitchMapPane.setOnMouseClicked(event -> {
try {

synchronized (sceneGraphLock) {
try {
final double clickX = event.getX();
final double clickY = event.getY();
event.consume();

synchronized (sceneGraphLock) {
try {

// locate image bounds, validate click, then:

Object lastMarker = pitchMapPane.getUserData();
if (lastMarker instanceof Node
oldMarker && oldMarker.getParent() == pitchMapPane) {

pitchMapPane.getChildren().remove(oldMarker);
}

ImageView ballView = new ImageView(new Image(getClass().getResourceAsStream("/images/cricket_ball.png")));
ballView.setFitWidth(12);
ballView.setFitHeight(12);
ballView.setPreserveRatio(true);
ballView.setLayoutX(clickX - 6);
ballView.setLayoutY(clickY - 6);

pitchMapPane.getChildren().add(ballView);
pitchMapPane.setUserData(ballView);

currentPitchMapX = clickX;
currentPitchMapY = clickY;
} catch (Exception ex) {
logger.error("Error in pitch map click handler (deferred)", ex);
}
}

} catch (Exception e) {
logger.error("Error in pitch map click handler", e);
}
}
} catch (Exception e) {
logger.error("Error in pitch map click handler", e);
}
});
}

if (ballArrivalPane != null) {
ballArrivalPane.setUserData(null);
ballArrivalPane.setOnMouseClicked(event ->  {
try {
synchronized (sceneGraphLock) {
try {
final double clickX = event.getX();
final double clickY = event.getY();
event.consume();

synchronized (sceneGraphLock) {
try {
Object lastMarker = ballArrivalPane.getUserData();
if (lastMarker instanceof Node oldMarker && oldMarker.getParent() == ballArrivalPane) {
ballArrivalPane.getChildren().remove(oldMarker);
}

ImageView ballView = new ImageView(new Image(getClass().getResourceAsStream("/images/cricket_ball.png")));
ballView.setFitWidth(12);
ballView.setFitHeight(12);
ballView.setPreserveRatio(true);
ballView.setLayoutX(clickX - 6);
ballView.setLayoutY(clickY - 6);

ballArrivalPane.getChildren().add(ballView);
ballArrivalPane.setUserData(ballView);

currentBallArrivalX = clickX;
currentBallArrivalY = clickY;
} catch (Exception ex) {
logger.error("Error in ball arrival click handler (deferred)", ex);
}
}

} catch (Exception e) {
logger.error("Error in ball arrival click handler", e);
}
}
} catch (Exception e) {
logger.error("Error in ball arrival click handler", e);
}
});
}

setupWagonWheelClickHandler();
// Initialize over and ball display
initializeOverBallDisplay();

// Initialize ball data table
initializeBallDataTable();

if (actionButton != null) {
actionButton.setText("Toss");
actionButton.setOnAction(e -> onActionButtonClick(e));
}
if (endBallButton != null) {
endBallButton.setOnAction(this::onEndBallClick);
}
setInitialState();

// Initially disable all UI elements except Toss button
setUIEnabled(false);

// Keep only Toss enabled before toss;  Edit/End Ball must remain disabled
if (actionButton != null) actionButton.setDisable(false);
if (endBallButton != null) endBallButton.setDisable(true);
if (editBallButton != null) editBallButton.setDisable(true);

// Initialize End Over button state
updateEndOverButtonState();

// Create floating tooltip for fielding zones
//        createFloatingTooltip();
// Ensure wagon wheel overlay starts disabled before toss
if (wagonWheelOverlay != null) {
wagonWheelOverlay.setDisable(true);
logger.info("Wagon wheel overlay disabled initially - will be enabled during ball capture");
}
// ✅ NEW: Add this line at the end of your existing initialize method
initializeManualRunSpinner();
initializeBallSpeedSpinner();
initializeInningDisplay();
// Initialize powerplay button click handler
initializePowerplayButton();
// Initialize powerplay configuration
initializePowerplayConfiguration();

// ✅ FIXED: Initialize partnership stats display
updatePartnershipStats();

setupTestMatchDropdownListeners();
// Initialize umpire dropdowns
initializeUmpireDropdowns();

// Initialize field tab components
initializeFieldTab();
}

private void setupWagonWheelClickHandler() {
wagonWheelOverlay.setOnMouseClicked(event -> {
try{
synchronized (sceneGraphLock) {
if (isModifyingSceneGraph || !isBallInProgress) return;

final double clickX = event.getX();
final double clickY = event.getY();
event.consume();

synchronized (sceneGraphLock) {
try {
final double wicketX = 124, wicketY = 96;

String detected = detectFieldingPosition(clickX, clickY);
if (detected != null) selectedFieldingPosition = detected;

List snapshot = new ArrayList(wagonWheelOverlay.getChildren());
List toRemove = new ArrayList();
for (Node node : snapshot) {
if (node instanceof Line || (node instanceof Circle && ((Circle) node).getRadius() == 4)) {
toRemove.add(node);
}
}
if (!toRemove.isEmpty()) {
wagonWheelOverlay.getChildren().removeAll(toRemove);
}

Line shotLine = new Line(wicketX, wicketY, clickX, clickY);
shotLine.setStroke(Color.YELLOW);
shotLine.setStrokeWidth(2);

Circle shotCircle = new Circle(clickX, clickY, 4);
shotCircle.setStroke(Color.YELLOW);
shotCircle.setFill(Color.YELLOW);

wagonWheelOverlay.getChildren().addAll(shotLine, shotCircle);
currentWagonWheelX = clickX;
currentWagonWheelY = clickY;
} catch (Exception e) {
logger.error("Error in wagon wheel click handler (deferred)", e);
}
}

}
} catch (Exception e) {
logger.error("Error in wagon wheel click handler", e);
}
});
}

private Circle createFieldingZone(String name, double x, double y, double radius) {
logger.info("Creating fieldingzoi zone: " + name + " at (" + x + ", " + y + ") with radius " + radius);
Circle zone = new Circle(x, y, radius);
// Store the zone name in userData for later retrieval
zone.setUserData(name);

// Make zones transparent for production
zone.setFill(Color.TRANSPARENT);
zone.setStroke(Color.TRANSPARENT);
zone.setCursor(Cursor.HAND);

zone.setOnMouseEntered(e ->  {
try {

synchronized (sceneGraphLock) {
if (isModifyingSceneGraph) return;
if (wagonWheelOverlay == null || wagonWheelOverlay.getScene() == null) return;

// Create temporary tooltip
Label tempTooltip = new Label(name);
tempTooltip.setStyle("-fx-background-color: #000000dd; -fx-text-fill: white; -fx-padding: 6 10; -fx-background-radius: 8;");
tempTooltip.setMouseTransparent(true);
wagonWheelOverlay.getChildren().add(tempTooltip);

// Position tooltip
tempTooltip.applyCss();
tempTooltip.layout();
double tooltipWidth = tempTooltip.getWidth();
if (tooltipWidth  paneWidth) {
offsetX = -tooltipWidth - 12;
}
if (mouseY + offsetY < 0) {
offsetY = 20;
}
if ((mouseX + offsetX + tooltipWidth > paneWidth) && (mouseY + offsetY < 0)) {
offsetX = -tooltipWidth - 12;
offsetY = 20;
}

tempTooltip.setLayoutX(mouseX + offsetX);
tempTooltip.setLayoutY(mouseY + offsetY);
tempTooltip.setVisible(true);

// Store reference for cleanup
zone.setUserData(new Object[]{name, tempTooltip});
}

} catch (Exception ex) {
logger.info("Error in mouse entered handler for fielding zone:1922 " + name, ex);
}
});

zone.setOnMouseMoved(e -> {
try {

synchronized (sceneGraphLock) {
if (isModifyingSceneGraph) return;

// Check if userData is an Object[] (tooltip was created)
Object userData = zone.getUserData();
if (!(userData instanceof Object[] data)) return; // Still just a String, no tooltip created

if (data == null || data.length < 2) return;

Label tempTooltip = (Label) data[1];
if (tempTooltip == null || !wagonWheelOverlay.getChildren().contains(tempTooltip)) return;

// Reposition existing tooltip
double mouseX = 0;
//                = e.getSceneX() - wagonWheelOverlay.localToScene(0, 0).getX();
double mouseY = 0;
//                = e.getSceneY() - wagonWheelOverlay.localToScene(0, 0).getY();
if (wagonWheelOverlay != null && wagonWheelOverlay.getScene() != null) {
Point2D offset = wagonWheelOverlay.localToScene(0, 0);
mouseX = e.getSceneX() - offset.getX();
mouseY = e.getSceneY() - offset.getY();
}

double paneWidth = wagonWheelOverlay.getWidth();
double tooltipWidth = tempTooltip.getWidth();

double offsetX = 12;
double offsetY = -28;

if (mouseX + offsetX + tooltipWidth > paneWidth) {
offsetX = -tooltipWidth - 12;
}
if (mouseY + offsetY < 0) {
offsetY = 20;
}
if ((mouseX + offsetX + tooltipWidth > paneWidth) && (mouseY + offsetY <  0)) {
offsetX = -tooltipWidth - 12;
offsetY = 20;
}

tempTooltip.setLayoutX(mouseX + offsetX);
tempTooltip.setLayoutY(mouseY + offsetY);
}
} catch (Exception ex) {
logger.info("Error in mouse moved handler for fielding zone:1973 " + name, ex);
}
});

zone.setOnMouseExited(e -> {
try {

synchronized (sceneGraphLock) {
if (isModifyingSceneGraph) return;

// Check if userData is an Object[] (tooltip was created)
Object userData = zone.getUserData();
if (!(userData instanceof Object[])) return;

Object[] data = (Object[]) userData;
if (data != null && data.length >= 2) {
Label tempTooltip = (Label) data[1];
if (tempTooltip != null) {
wagonWheelOverlay.getChildren().remove(tempTooltip);
}
}
}
}
catch (Exception ex) {
logger.info("Error in mouse exited handler for fielding zone:1998 " + name, ex);
}
});
logger.info("Created fielding zone: " + name);
return zone;
}
private void clearBallPositionMarkers() {
if (pitchMapPane == null && wagonWheelOverlay == null && ballArrivalPane == null) return;

// Mark as modifying so any filters can block mouse events
isModifyingSceneGraph = true;

// Stage 1: make panes non-pickable to avoid pick/layout races during removals
if (pitchMapPane != null) {
pitchMapPane.setMouseTransparent(true);
pitchMapPane.setPickOnBounds(false);
}
if (wagonWheelOverlay != null) {
wagonWheelOverlay.setMouseTransparent(true);
wagonWheelOverlay.setPickOnBounds(false);
}
if (ballArrivalPane != null) {
ballArrivalPane.setMouseTransparent(true);
ballArrivalPane.setPickOnBounds(false);
}

synchronized (sceneGraphLock) {
try {
// Pitch map
if (pitchMapPane != null) {
Object last = pitchMapPane.getUserData();
if (last instanceof Node n && n.getParent() == pitchMapPane) {
n.setVisible(false);
pitchMapPane.getChildren().remove(n);
}
pitchMapPane.setUserData(null);
}

// Wagon wheel (with fresh pane, just remove shot elements)
if (wagonWheelOverlay != null) {
List snapshot = new ArrayList(wagonWheelOverlay.getChildren());
List toRemove = new ArrayList();
for (Node node : snapshot) {
if (node instanceof Line || (node instanceof Circle && ((Circle) node).getRadius() == 4)) {
toRemove.add(node);
}
}
if (!toRemove.isEmpty()) {
wagonWheelOverlay.getChildren().removeAll(toRemove);
}
}

// Ball arrival
if (ballArrivalPane != null) {
Object last = ballArrivalPane.getUserData();
if (last instanceof Node n && n.getParent() == ballArrivalPane) {
n.setVisible(false);
ballArrivalPane.getChildren().remove(n);
}
ballArrivalPane.setUserData(null);
}
} catch (Exception e) {
logger.error("Error clearing markers", e);
}
}

// Force a layout pass while panes are non-pickable
if (wagonWheelOverlay != null) { wagonWheelOverlay.applyCss(); wagonWheelOverlay.layout(); }
if (pitchMapPane != null) { pitchMapPane.applyCss(); pitchMapPane.layout(); }
if (ballArrivalPane != null) { ballArrivalPane.applyCss(); ballArrivalPane.layout();  }

try {
if (pitchMapPane != null) {
pitchMapPane.setPickOnBounds(true);
pitchMapPane.setMouseTransparent(false);
}
if (wagonWheelOverlay != null) {
wagonWheelOverlay.setPickOnBounds(true);
wagonWheelOverlay.setMouseTransparent(false);
}
if (ballArrivalPane != null) {
ballArrivalPane.setPickOnBounds(true);
ballArrivalPane.setMouseTransparent(false);
}
} finally {
isModifyingSceneGraph = false;
}

}
//здесь есть исключение: получение неоднократно не может получить строку кода, отвечающую за это, а также происходит в цикле и зависает все приложение

Код: Выделить всё

    Thread: JavaFX Application Thread
Exception: java.lang.IndexOutOfBoundsException
Message: Index -1 out of bounds for length 3
Full Stack Trace:
java.lang.IndexOutOfBoundsException:  Index -1 out of bounds for length 3
at java.base/jdk.internal.util.Preconditions.outOfBounds(Unknown Source)
at java.base/jdk.internal.util.Preconditions.outOfBoundsCheckIndex(Unknown Source)
at java.base/jdk.internal.util.Preconditions.checkIndex(Unknown Source)
at java.base/java.util.Objects.checkIndex(Unknown Source)
at java.base/java.util.ArrayList.get(Unknown Source)
at javafx.base/com.sun.javafx.collections.ObservableListWrapper.get(Unknown Source)
at javafx.base/com.sun.javafx.collections.VetoableListDecorator.get(Unknown Source)
at javafx.graphics/javafx.scene.Parent.updateCachedBounds(Unknown Source)
at javafx.graphics/javafx.scene.Parent.recomputeBounds(Unknown Source)
at javafx.graphics/javafx.scene.Parent.doComputeGeomBounds(Unknown Source)
at javafx.graphics/javafx.scene.Parent$1.doComputeGeomBounds(Unknown Source)
at javafx.graphics/com.sun.javafx.scene.ParentHelper.computeGeomBoundsImpl(Unknown Source)
at javafx.graphics/com.sun.javafx.scene.layout.RegionHelper.superComputeGeomBoundsImpl(Unknown Source)
at javafx.graphics/com.sun.javafx.scene.layout.RegionHelper.superComputeGeomBounds(Unknown Source)
at javafx.graphics/javafx.scene.layout.Region.doComputeGeomBounds(Unknown Source)
at javafx.graphics/javafx.scene.layout.Region$1.doComputeGeomBounds(Unknown Source)
at javafx.graphics/com.sun.javafx.scene.layout.RegionHelper.computeGeomBoundsImpl(Unknown Source)
at javafx.graphics/com.sun.javafx.scene.NodeHelper.computeGeomBounds(Unknown Source)
at javafx.graphics/javafx.scene.Node.updateGeomBounds(Unknown Source)
at javafx.graphics/javafx.scene.Node.getGeomBounds(Unknown Source)
at javafx.graphics/javafx.scene.Node.getLocalBounds(Unknown Source)
at javafx.graphics/javafx.scene.Node.intersectsBounds(Unknown Source)
at javafx.graphics/javafx.scene.Node$1.intersectsBounds(Unknown Source)
at javafx.graphics/com.sun.javafx.scene.NodeHelper.intersectsBounds(Unknown Source)
at javafx.graphics/javafx.scene.layout.Region.doPickNodeLocal(Unknown Source)
at javafx.graphics/javafx.scene.layout.Region$1.doPickNodeLocal(Unknown Source)
at javafx.graphics/com.sun.javafx.scene.layout.RegionHelper.pickNodeLocalImpl(Unknown Source)
at javafx.graphics/com.sun.javafx.scene.NodeHelper.pickNodeLocal(Unknown Source)
at javafx.graphics/javafx.scene.Node.pickNode(Unknown Source)
at javafx.graphics/javafx.scene.Scene$MouseHandler.pickNode(Unknown Source)
at javafx.graphics/javafx.scene.Scene.pick(Unknown Source)
at javafx.graphics/javafx.scene.Scene$MouseHandler.process(Unknown Source)
at javafx.graphics/javafx.scene.Scene.processMouseEvent(Unknown Source)
at javafx.graphics/javafx.scene.Scene$ScenePeerListener.mouseEvent(Unknown Source)
at javafx.graphics/com.sun.javafx.tk.quantum.GlassViewEventHandler$MouseEventNotification.run(Unknown Source)
at javafx.graphics/com.sun.javafx.tk.quantum.GlassViewEventHandler$MouseEventNotification.run(Unknown Source)
at java.base/java.security.AccessController.doPrivileged(Unknown Source)
at javafx.graphics/com.sun.javafx.tk.quantum.GlassViewEventHandler.lambda$handleMouseEvent$2(Unknown Source)
at javafx.graphics/com.sun.javafx.tk.quantum.QuantumToolkit.runWithoutRenderLock(Unknown Source)
at javafx.graphics/com.sun.javafx.tk.quantum.GlassViewEventHandler.handleMouseEvent(Unknown Source)
at javafx.graphics/com.sun.glass.ui.View.handleMouseEvent(Unknown Source)
at javafx.graphics/com.sun.glass.ui.View.notifyMouse(Unknown Source)
at javafx.graphics/com.sun.glass.ui.win.WinApplication._runLoop(Native Method)
at javafx.graphics/com.sun.glass.ui.win.WinApplication.lambda$runLoop$3(Unknown Source)
at java.base/java.lang.Thread.run(Unknown Source)

Я пробовал
Использовать setAll() вместоclear() + addAll()

Установка setVisible(false) во время изменений

Добавление флагов isModifyingSceneGraph

Ошибка по-прежнему периодически возникает при наведении курсора мыши на

интерактивные элементы во время сцены изменения графа ставятся в очередь через

Platform.runLater()

Подробнее здесь: https://stackoverflow.com/questions/797 ... im-getting
Ответить

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

Вернуться в «JAVA»