Код: Выделить всё
// here is my initialize method and create fileding zones in which i
// am having some
// declaration of mouse effects
// in this code i am working on three images two having click effect
// dropping ball image on click on them
// one code for wagon wheel which also has hover effect and click effect
// all image have code of set and reset and clear**
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 flag Guards
Ошибка по-прежнему периодически возникает при наведении курсора мыши на
интерактивные элементы, когда изменения графа сцены ставятся в очередь с помощью
Platform.runLater()
Подробнее здесь: https://stackoverflow.com/questions/797 ... im-getting
Мобильная версия