< prev index next >

modules/javafx.controls/src/main/java/javafx/scene/control/ControlUtils.java

Print this page
rev 10463 : 8089514: [TableView, TreeView, ListView, TreeTableView] Clicking outside of the edited cell, node, or entry should commit the value

@@ -1,7 +1,7 @@
 /*
- * Copyright (c) 2013, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013, 2017, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
  * under the terms of the GNU General Public License version 2 only, as
  * published by the Free Software Foundation.  Oracle designates this

@@ -31,12 +31,13 @@
 import javafx.event.Event;
 import javafx.scene.Node;
 import javafx.scene.Parent;
 import javafx.scene.Scene;
 
-import java.util.ArrayList;
 import java.util.List;
+import java.util.Optional;
+import java.util.function.Function;
 import java.util.stream.Collectors;
 
 class ControlUtils {
     private ControlUtils() { }
 

@@ -51,24 +52,43 @@
             control.fireEvent(new ScrollToEvent<TableColumnBase<?, ?>>(control, control, ScrollToEvent.scrollToColumn(), column));
         });
     }
 
     static void requestFocusOnControlOnlyIfCurrentFocusOwnerIsChild(Control c) {
-        Scene scene = c.getScene();
+        runOnFocusedNodeIfChildOf(c, matchingNode -> {
+            matchingNode.requestFocus();
+            return null;
+        });
+    }
+
+    static boolean isFocusOnNodeOrAnyChild(final Node n) {
+        return runOnFocusedNodeIfChildOf(n, matchingNode -> true).orElse(false);
+    }
+
+    static <R> Optional<R> runOnFocusedNodeIfChildOf(final Node n, Function<Node, R> f) {
+        if (n == null) return Optional.empty();
+        if (n.isFocused()) {
+            return Optional.ofNullable(f.apply(n));
+        }
+
+        Scene scene = n.getScene();
         final Node focusOwner = scene == null ? null : scene.getFocusOwner();
+
         if (focusOwner == null) {
-            c.requestFocus();
-        } else if (! c.equals(focusOwner)) {
+            return Optional.empty();
+        } else if (n.equals(focusOwner)) {
+            return Optional.ofNullable(f.apply(n));
+        } else {
             Parent p = focusOwner.getParent();
             while (p != null) {
-                if (c.equals(p)) {
-                    c.requestFocus();
-                    break;
+                if (n.equals(p)) {
+                    return Optional.ofNullable(f.apply(p));
                 }
                 p = p.getParent();
             }
         }
+        return Optional.empty();
     }
 
     static <T> ListChangeListener.Change<T> buildClearAndSelectChange(
             ObservableList<T> list, List<T> removed, int retainedRow) {
         return new ListChangeListener.Change<T>(list) {
< prev index next >