2013-07-18 97 views
3

我正在使用JavaFX中的TableView。我想要做的是跟蹤對桌子的編輯。當用戶離開表格時,我想檢查是否有任何編輯,如果是,請提示用戶詢問他們是否要保存其更改。在JavaFX中,我如何確定獲得焦點的節點是否是我自己的子節點?

我有TableView的工作,我可以跟蹤編輯,我可以確定何時TableView失去焦點(使用focusedProperty更改偵聽器)。

但是,問題在於,當單擊單元格進行編輯時,focusedProperty會更改表格觸發器的偵聽器(編輯單元獲得焦點,表格本身會丟失它)。我真正想要的是一種判斷當焦點發生變化時是否變爲表格的子節點(如列或單元格)或表格之外的內容(在父GUI上選擇不同的選項卡)的方法。但是我不想將偵聽器添加到其他可能點擊的節點上。我可以遞歸地調用getParent()並檢查TableView是否在列表中,如果是的話,我會知道如何獲取當前關注的項目(沒有看到如何做到這一點)知道這是一個孩子。但是我還沒有看到一種通用的方式來獲取應用程序中當前關注的節點。因爲getChildrenUnmodifiable()返回給我Node()類型(我想我可以將每個類型轉換爲確定它們是否每個都有更多的子元素),或者我必須通過這個方法來遍歷表中的子元素,否則我不得不以去TableColumns然後去那裏的單元格(並檢查每個單元格的圖形)。

我可能會用迭代迭代,根據需要進行投射,並在此時檢查isFocused(),除非有更好的解決方案。但我希望這裏有人可能有更好的解決方案來解決這個問題,最好是更通用的解決方案。

回答

6

我從一個節點進行搜索,投射給孩子,並檢查重點節點是否是孩子。這不是優雅 - 它肯定覺得應該有更好的方法。但這裏是我用來做這樣的方法:

private boolean isChildFocused(javafx.scene.Parent parent) 
{ 
    for (Node node : parent.getChildrenUnmodifiable()) 
    { 
     if (node.isFocused()) 
     { 
      return true; 
     } 
     else if (node instanceof javafx.scene.Parent) 
     { 
      if (isChildFocused((javafx.scene.Parent)node)) 
      { 
       return true; 
      } 
     } 
    } 
    return false; 
} 

這似乎很好地工作(至少使用一個TableView中爲根級父),調用這個時候的假父變化focusedProperty()(通過屬性更改監聽器)。

4

您可以通過場景的getFocusOwner()或focusOwnerProperty()獲取當前焦點的節點。正如你所說,從聚焦節點到TableView的遍歷更好。

public void createTable() { 
     TableView tableView = new TableView(); 
     tableView.focusedProperty().addListener((ObservableValue<? extends Boolean> observable, Boolean oldValue, Boolean newValue) -> { 
      if (oldValue && !newValue) { 
       if (!isParent(tableView, tableView.getScene().getFocusOwner())) { 
        System.out.println("Saving changes."); 
       } 
      } 
     }); 
    } 

    public boolean isParent(Parent parent, Node child) { 
     if (child == null) { 
      return false; 
     } 
     Parent curr = child.getParent(); 
     while (curr != null) { 
      if (curr == parent) { 
       return true; 
      } 
      curr = curr.getParent(); 
     } 
     return false; 
    } 
相關問題