2016-12-05 13 views
2

TilePaneの画像を表示するScrollPaneがあります。それらの画像の1つを削除するたびに、ScrollPaneが先頭にジャンプします。これは、複数の画像を削除しようとすると非常に面倒です。スクロール動作を制御する方法はありますか?ノードを削除するときにScrollPaneが上に移動する

私は、Windows 7上でこのコードを実行している:

import javafx.application.Application; 
import javafx.event.ActionEvent; 
import javafx.event.EventHandler; 
import javafx.scene.Scene; 
import javafx.scene.control.Button; 
import javafx.scene.control.ScrollPane; 
import javafx.scene.image.ImageView; 
import javafx.scene.layout.BorderPane; 
import javafx.scene.layout.StackPane; 
import javafx.scene.layout.TilePane; 
import javafx.stage.Stage; 

public class ScrollbarProblem extends Application{ 
    private TilePane imagePane; 
    private ScrollPane scroller; 

    @Override 
    public void start(Stage primaryStage) { 
     imagePane = new TilePane(); 
     scroller = new ScrollPane(); 
     scroller.setContent(imagePane); 
     BorderPane root = new BorderPane(scroller, null, null, null, null); 
     Scene scene = new Scene(root, 800, 600); 
     primaryStage.setScene(scene); 
     primaryStage.show(); 

     for(int i = 0; i < 20; i++){ 
      Image img = new Image("https://upload.wikimedia.org/wikipedia/commons/thumb/b/b6/SIPI_Jelly_Beans_4.1.07.tiff/lossy-page1-220px-SIPI_Jelly_Beans_4.1.07.tiff.jpg"); 
      final ImageView imageView = new ImageView(img); 

      final Button button = new Button("Delete"); 
      final StackPane stackPane = new StackPane(); 

      button.setOnAction(new EventHandler<ActionEvent>() { 

       @Override 
       public void handle(ActionEvent event) { 
        imagePane.getChildren().remove(stackPane); 
       } 
      }); 

      stackPane.getChildren().addAll(imageView, button); 
      imagePane.getChildren().add(stackPane); 
     } 
    } 

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

奇妙に聞こえます。..問題を示す[MCVE]を含めるように質問を編集できますか? –

+0

私は小さな例を編集しました。 – Simoon

答えて

2

ScrollPaneがフォーカスされたNodeがビューポート内に表示される確認します。クリックされたButtonがフォーカスしています。これは、フォーカスされたノードが削除され、JavaFXがScrollPaneコンテンツ(この場合は最初のButton)の別のノードにフォーカスを移動しようとしていることを意味します。 ScrollPaneは、このノードをビューにスクロールし、観察された動作を説明します。

解決策は、ButtonfocusTraversableプロパティをfalseに設定することです。これは、この行動に責任方法ですので、まだあなたがタブを経由してフォーカスを変更することができるようになる

別のオプションは、ScrollPaneSkinonTraverseメソッドをオーバーライドすることになります。

scroller.setSkin(new ScrollPaneSkin(scroller) { 

    @Override 
    public void onTraverse(Node n, Bounds b) { 
    } 

}); 
+0

ボタンをタブで移動することは意図されていないので、あなたのソリューションはさらに簡単です。ありがとう! – Simoon

2

問題はタイルペインの最初の要素のボタンに戻すフォーカスに起因すると思われます。一つの回避策は次のとおりです。

Image img = new Image(
     "https://upload.wikimedia.org/wikipedia/commons/thumb/b/b6/SIPI_Jelly_Beans_4.1.07.tiff/lossy-page1-220px-SIPI_Jelly_Beans_4.1.07.tiff.jpg"); 

for (int i = 0; i < 20; i++) { 
    final ImageView imageView = new ImageView(img); 

    final Button button = new Button("Delete"); 
    final StackPane stackPane = new StackPane(); 


    button.setOnAction(new EventHandler<ActionEvent>() { 

     @Override 
     public void handle(ActionEvent event) { 

      int index = imagePane.getChildren().indexOf(stackPane); 

      imagePane.getChildren().remove(index); 
      int numPanes = imagePane.getChildren().size(); 
      if (numPanes > 0) { 
       imagePane.getChildren().get(Math.min(index, numPanes-1)).requestFocus(); 
      } 
     } 
    }); 

    stackPane.getChildren().addAll(imageView, button); 
    imagePane.getChildren().add(stackPane); 
} 
+0

それが問題でした。ありがとう! – Simoon

関連する問題