JavaFX 2.0 TableView - Navigation of TableView Cell Factory using Keyboard

Hi All,
I have a particular query as regards a JavaFX TableView, specifically cell Navigation using the arrow Keys on the keyboard.
I have a TableView of multiple rows and columns. Inside each of the table cells i have created a cellfactory that turns each of the cells into a TextInput Field. Essentially i am trying to create a good old Excel Spreadsheet in terms of look and feel. Although now i have the cellfactory and functionality working the way i would like, I have come accross an issue though in terms of the navigation using the keyboard arrow keys.
I was wondering if anyone could advise as regards, how i can get the focus of the TextInput within my tableCell that im currently in, and then be able to move up/down/left/right using the keys without going out of the bounds of the TableView. Surely this has be built in to the API, or am i having this problem as im using a custom cell factory?
I have read that in 2.2 there is improved nav functionality but we are not there yet and am trying to work around this issue.
Input greatly appreciated
Thanks

I have made such features in my application, you can achieve this by adding event listener to TextCell:
textField.setOnKeyReleased(new EventHandler< KeyEvent>() {
public void handle(KeyEvent t) {
if (t.getCode() == KeyCode.ENTER) {
commitEdit(textField.getText());
getTableView().getFocusModel().focusRightCell();
getTableView().edit(getTableRow().getIndex(), getTableView().getFocusModel().getFocusedCell().getTableColumn());
.....

Similar Messages

  • ITunes 11.2.0.114 Library Navigation no longer works by using keyboard shortcuts

    In particular, when viewing my library via the "Albums" tab, I can no longer navigate to an artist simply by starting to type their corresponding letter. For example, before I updated to version 11.2.0.114 yesterday, I was able to type in the letter "s" and I would be navigated to the beginning of all the artists in my library starting with the letter "s". Likewise, if I would continue to type, "sa..." it would navigate to the corresponding artist/place in my library.
    Now when I try to navigate through my library in this manner, it seems as if the letters have no meaning anymore; typing in "s" could bring me to artists in the "b" range.
    I am using Windows 8. Please help if you can!
    Thank you.

    Exactly the same problem with me - iTunes 12.2.2, on OS X 10.9.3. It was perfect one day, then bam, the next day the keyboard shortcuts stopped working properly. It's pretty frustrating.

  • How to dynamically load an Image into a TableView when its row/cell becomes visible?

    Hi,
    I am building an application that shows tables with large amounts of data containing columns that should display a thumbnail. However, this thumbnail is supposed to be loaded in the background lazily, when a row becomes visible because it is computationally too expensive to to this when the model data is loaded and typically not necessary to retrieve the thumbnail for all data that is in the table.
    I have done the exact same thing in the past in a Swing application by doing this:
    Whenever the model has changed or the vertical scrollbar has moved:
    - Render a placeholder image in the custom cell renderer for this JTable if no image is available in the model object representing the corresponding row
    - Compute the visible rows by using getVisibleRect and rowAtPoint methods in JTable
    - Start a background thread that retrieves the image for the given rows and sets the resulting BufferedImage in a custom Model Object that was used in the TableModel (if not already there because of an earlier run)
    - Fire a corresponding model change event in the EDT whenever an image has been retrieved in the background thread so the row is rendered again
    Btw. the field in the model class holding the BufferedImage was a weak reference in this case so the memory can be reclaimed as needed by the application.
    What is the best way to achieve this behaviour using a JFX TableView? I have so far failed to find anything in the API to retrieve the visible items/rows. Is there a completely different approach available/required that uses the Cell API? I fail to see it so far.
    Thanks in advance for any hints here.

    Here’s what I have tried so far:
    I have defined a property in my model object that contains a weak reference to the image that is expensive to load. I have modeled that reference as an inner class to the object so I have a reference to its enclosing object. That is necessary because my cell factory otherwise has no access to the enclosing model object, which it needs to trigger loading the image in the background.
    The remaining problems I have is, that I don’t have sufficient control over the loading process, i.e. I need to delay the loading process until scrolling has stopped and abort it as soon as the user starts scrolling again and the visible content changes. Imagine that loading an image for a table row (e.g. a thumbnail for a video) takes 200ms to load and a user quickly scrolls through a few hundred records and then stops. With my current set-up, the user has to wait for all loading processes that were triggered in the cell factories to finish until the thumbnails of the records they are looking at will appear (imagine an application like finder to be implemented like that, it would simply suck UX-wise). In my swing application a background thread that loads images for the visible records is triggered with a delay and stopped as soon as the visible content changes. This works well enough for a good user experience. I don’t see how I can do this based on the cell API. It is nice to have all this abstracted away but in this case I do not see how I can achieve the same user experience as in my swing application.
    I also tried registering a change listener to the TreeCell’s visible property to make that control the image loading but I don’t seem to get any change events at all when I do that.
    I must be missing something.

  • Tableview navigation

    Hi,
    I am trying to implement navigation event for my table view. For some reason, the event is not being captured.
    I am trying to print a test message in the event implementation which is not printing, which means the event is not being captured.
    Here is my Dynpage code:
         public void onMyOnNavigate(Event event) throws PageException {
              IPortalComponentResponse response = (IPortalComponentResponse) this.getResponse();
              response.write("Navigate Event ");     
              TableNavigationEvent tne = (TableNavigationEvent) event;
              if (myBean != null) {
                   myBean.setVisibleFirstRow(new Integer(tne.getFirstVisibleRowAfter()).toString());
    here is the JSP tableview declaration:
                <hbj:tableView
                  id="myTableView1"
                  model="myBean.model"
                  design="ALTERNATING"
                  headerVisible="true"
                  footerVisible="true"
                  fillUpEmptyRows="true"
                  navigationMode="BYLINE"
                  selectionMode="MULTISELECT"
                  headerText="Compitency History"
                  onNavigate="myOnNavigate"
                  visibleFirstRow="1"
                  visibleRowCount="4"
                  width="500 px">
              </hbj:tableView>
    And here is the bean code:
         public void setVisibleFirstRow(String visibleFirstRow) {
              this.visibleFirstRow = visibleFirstRow;
         public String getVisibleFirstRow() {
              return visibleFirstRow;
    Can anyone tell me where am I going wrong..
    (I even tried changing the event name to myOnNavigate
    from onMyOnNavigate, but still it didn't work)
    -Sudheer

    result sounds like a very common name, likely this and similiar words are already used ...
    In general, it is a good ides to maybe prefix your IDs, this avoids problems with existing IDs or functions:
    For example, <b>tv_</b>result (tv for tableview).
    In our current application I have a 60kb+ javascript file, lots of functions and variables in there, all are prefixed the one way or another, didn't run into any duplicate-name problems yet.

  • JavaFX 8 TableColumn CellValueFactory invoked for every cell update -- normal??

    Hi!  I have a JavaFX 8 TableView with multiple columns.  The CellValueFactories for the columns are set as:
        xxxColumn.setCellValueFactory(new ItemCountFactory(itemName));   where itemName is a String identifying a different item for each column.
    ItemCountFactory returns a StringBinding as the cell value, as follows:
        public ObservableValue<String> call(CellDataFeatures<Category, String> rowData) {
            return new ItemCountBinding(rowData.getValue(), itemName);
    where
         class ItemCountBinding extends StringBinding {
              protected String computeValue() {
                        String cellValue = ...;
                        return cellValue;
    The StringBinding depends on properties of the Category instance for the table row.  The correct data is displayed okay, but I have noticed that every time one of the Category properties changes (i.e., every time a cell value changes), ItemCountFactory is called again to create a new StringBinding.  I would have expected the Factory to be invoked just once for each cell during initialization, and then the table column would monitor the returned Observable object.  Instead it seems to be creating a new Observable object every time the cell value changes.  Is this normal, or am I doing something wrong?  Same behavior on Java 8u20 and 8u40.  If it is not the expected behavior, I will write an example test program; I do not want to post the current full source code.
    The table items are set just once, with:
         countTable.setItems(categoryList);
    where categoryList is of type ObservableList<Category>.  The list itself is not modified after being associated with the table; i.e., no rows are added or deleted or replaced.
    Thanks for any insights!

    Good. I'll assume the request for an mcve indicates that this behavior is not expected.  Here's a minimal example.  The cell value factory returns an observable StringBinding to provide the cell contents.  Instead of just monitoring the initial StringBinding for changes, TableColumn calls the cell value factory and creates a new StringBinding every time the value changes. 
    I couldn't find how to attach files to a reply, so 3 source files are inserted inline below.  Thanks for any insights. I want to make sure I'm not using the Java FX concepts incorrectly.
    CellValueFactoryTest.java:
    package test;
    import javafx.application.Application;
    import static javafx.application.Application.launch;
    import javafx.collections.FXCollections;
    import javafx.collections.ObservableList;
    import javafx.event.ActionEvent;
    import javafx.scene.Scene;
    import javafx.scene.control.Button;
    import javafx.scene.control.TableColumn;
    import javafx.scene.control.TableView;
    import javafx.scene.layout.VBox;
    import javafx.stage.Stage;
    * Minimal test program to demonstrate a CellValueFactory being
    * called every time a cell value changes.
    public class CellValueFactoryTest extends Application {
        // This list contains the items for the table view
        private ObservableList<RowData> tableData;
         * Build a scene and make it visible.
         * @param primaryStage The window in which to display the program output.
        @Override
        public void start(Stage primaryStage) {
            // Create a table with one row and one column
            TableView demoTable = new TableView();
            tableData = FXCollections.observableArrayList();
            tableData.add(new RowData());
            demoTable.setItems(tableData);
            TableColumn countCol = new TableColumn();
            countCol.setText("Count");
            countCol.setCellValueFactory(new CountValueFactory());
            demoTable.getColumns().add(countCol);
            // Add a button to increment the cell value in the first table row.
            // This action causes the CellValueFactory to be invoked again to
            // create a new ObservableValue for the cell, which seems unnecessary.
            // Shouldn't the existing ObservableValue be kept and just monitored?
            Button testButton = new Button("Test");
            testButton.setOnAction((ActionEvent event) -> tableData.get(0).increment());
            // build scene
            VBox root = new VBox(10, demoTable, testButton);
            Scene scene = new Scene(root);
            primaryStage.setTitle("CellValueFactory Test");
            primaryStage.setScene(scene);
            primaryStage.show();
         * Main entry point for the program.
         * @param args the command line arguments
        public static void main(String[] args) {
            launch(args);
    RowData.java:
    package test;
    import javafx.beans.property.IntegerProperty;
    import javafx.beans.property.SimpleIntegerProperty;
    * Represents one row of a table.  For demo purposes,
    * the row data contains only one variable.
    class RowData {
        // A simple integer property to count button clicks
        private final IntegerProperty count = new SimpleIntegerProperty();
        public int getCount() {
            return count.get();
        public void setCount(int value) {
            count.set(value);
        public IntegerProperty countProperty() {
            return count;
        public RowData() {
            count.set(0);
         * Increment the count property.
        public void increment() {
            count.set(count.get() + 1);
    CountValueFactory.java:
    package test;
    import javafx.beans.binding.StringBinding;
    import javafx.beans.value.ObservableValue;
    import javafx.scene.control.TableColumn;
    import javafx.util.Callback;
    * A CellValueFactory that returns an observable String to provide the cell contents.
    * One would expect this class to be invoked once to provide an Observable object;
    * after which the TableColumn would just monitor the Observable's value.  Instead,
    * TableColumn invokes this class to create a new Observable every time the Observable's
    * value changes.
    class CountValueFactory implements Callback<TableColumn.CellDataFeatures<RowData, String>, ObservableValue<String>>  {
        public CountValueFactory() {
         * Provide an observable value to display in the table cell.  The value depends
         * on one property: the number of button clicks recorded in the RowData instance.
         * @param param Identifies the RowData instance for this table cell
         * @return an Observable String containing the count of button clicks.
        @Override
        public ObservableValue<String> call(TableColumn.CellDataFeatures<RowData, String> cellInfo) {
            RowData rowData = cellInfo.getValue();
            System.out.println("Cell value factory invoked. Creating a new StringBinding to represent the cell contents. "
                    + "Current click count = " + rowData.getCount());
            return new CellValueBinding(rowData);
         * An observable string to provide the table cell contents.  In this demo case it depends on a
         * single property of the row data.  In real life it depends on multiple properties.
        private static class CellValueBinding extends StringBinding {
            // same the RowData instance for this cell
            private final RowData buttonClickCounts;
             * Constructor
             * @param rowData The RowData instance that provides data for this row.
            public CellValueBinding(RowData rowData) {
                buttonClickCounts = rowData;
                bind(rowData.countProperty());
             * Format the table cell value when the underlying dependency changes.
             * @return A string containing the number of button clicks.
            @Override
            protected String computeValue() {
                return buttonClickCounts.getCount() + " clicks";

  • What exactly is the "cell factory?"

    So I've been seeing this term a lot on the forums, as well as http://docs.oracle.com/javafx/2/ui_controls/table-view.htm and on the ensemble, but I'm not 100% sure what it is.... It seems like just a method to set data into your tables, like the table model? Anyone have a more in depth explanation than the one in the docs, I would appreciate it!!!
    Thanks,
    ~KZ

    Cell factories create cells. A cell is a Labeled Node which contains some extra properties and methods for maintaining an editing and selection state and a link back to a cell value. Cells are used in a few places in JavaFX, for example in ListViews and TableViews, as well as TreeTables and ComboBoxes. The Cell is the visual representation (Node) which corresponds to a backing data item. The trick is that there is not necessarily a static one to one correspondence between cells and data values.
    Let's take an example. Here is an empty ListView in a Scene. When I run the app, it displays the ListView at it's preferred height, with 17 rows.
    import javafx.application.Application;
    import javafx.scene.Scene;
    import javafx.scene.control.ListView;
    import javafx.scene.layout.*;
    import javafx.stage.Stage;
    public class ListViewSample extends Application {
      @Override public void start(Stage stage) {
        ListView listView = new ListView();
        VBox layout = new VBox();
        VBox.setVgrow(listView, Priority.ALWAYS);
        layout.getChildren().addAll(listView);
        stage.setScene(new Scene(layout));
        stage.show();
      public static void main(String[] args) { launch(args); }
    }Each one of those 17 rows is empty. No Cell Factory has been set, yet you can see alternating light and dark shaded rows. Each one of these rows in the ListView corresponds to a Cell and each cell has been generated by the default ListView cell factory. When I drag the stage's bottom border to increase the size of the stage, the list view increases in size. When I drag the stage's bottom border to decrease the size of the stage, the list view decreases in size. When the list view increases in size, more rows are visible. Each of the new cells for the larger list view are generated by the cell factory on an as needed basis; i.e. the cells were not created when the app was first run but only created as there was a greater visible area available to the ListView in which the ListView could display more cells.
    Now everything is pretty boring so far. Let's add some data, using the following line of code:
    listView.setItems(FXCollections.observableArrayList("apple", "orange", "pear"));Now you will see the strings "apple", "orange" and "pear" rendered in the first three cells of the ListView again by using the default cell factory for the ListView. Again this is pretty boring.
    What we will do now is add some mutators which will change the observable list backing the list view in response to some user actions:
    import javafx.application.Application;
    import javafx.collections.FXCollections;
    import javafx.event.*;
    import javafx.scene.Scene;
    import javafx.scene.control.*;
    import javafx.scene.layout.*;
    import javafx.stage.Stage;
    import java.util.Collections;
    import java.util.Comparator;
    public class ListViewSample extends Application {
      @Override public void start(Stage stage) {
        final ListView<String> listView = new ListView<>();
        listView.setItems(FXCollections.observableArrayList("apple", "orange", "pear"));
        ListViewSorter listViewSorter = new ListViewSorter(listView).invoke();
        VBox layout = new VBox(10);
        VBox.setVgrow(listView, Priority.ALWAYS);
        listView.setMinHeight(0);
        layout.getChildren().addAll(
            listView,
            HBoxBuilder
                .create()
                .spacing(10)
                .children(
                    guavaCreator(listView),
                    listViewSorter.getSorter(),
                    listViewSorter.getReverser()
                .build()
        stage.setScene(new Scene(layout));
        stage.show();
      private Button guavaCreator(final ListView<String> listView) {
        final Button guavatron = new Button("Add Guava");
        guavatron.setOnAction(new EventHandler<ActionEvent>() {
          @Override public void handle(ActionEvent actionEvent) {
            listView.getItems().add("guava");
            guavatron.setDisable(true);
        return guavatron;
      public static void main(String[] args) { launch(args); }
      private class ListViewSorter {
        private final ListView<String> listView;
        private Button sorter;
        private Button reverser;
        public ListViewSorter(ListView<String> listView) {
          this.listView = listView;
        public Button getSorter() {
          return sorter;
        public Button getReverser() {
          return reverser;
        public ListViewSorter invoke() {
          sorter = new Button("Sort");
          sorter.setOnAction(new EventHandler<ActionEvent>() {
            @Override public void handle(ActionEvent actionEvent) {
              Collections.sort(listView.getItems());
          final Comparator<String> REVERSE_SORT = new Comparator<String>() {
            @Override  public int compare(String s1, String s2) {
              return -1 * s1.compareTo(s2);
          reverser = new Button("Reverse Sort");
          reverser.setOnAction(new EventHandler<ActionEvent>() {
            @Override public void handle(ActionEvent actionEvent) {
              Collections.sort(listView.getItems(), REVERSE_SORT);
          return this;
    }OK, now we have some extra buttons, the "Add guava" button will create a new item ("guava"), the "Sort" and "Reverse Sort", buttons will change the sort order of the backing list. Now to understand what happens behind the scenes when we use these buttons, let's take a look at the source code for the default list cell factory.
    new ListCell() {
       @Override public void updateItem(Object item, boolean empty) {
         super.updateItem(item, empty);
         if (empty) {
           setText(null);
           setGraphic(null);
         } else if (item instanceof Node) {
           setText(null);
           Node currentNode = getGraphic();
           Node newNode = (Node) item;
           if (currentNode == null || ! currentNode.equals(newNode)) {
             setGraphic(newNode);
         } else {
           setText(item == null ? "null" : item.toString());
           setGraphic(null);
    };This code is doing one of three things. If the list cell is empty, it sets the text and graphic to null, so you end up with a blank cell (the alternating light and dark grey bars are generated by the ListCell's parent setting differing style classes on alternate cells). If the item is a node, it sets the graphic to the node - this is the mechanism which allow you to place nodes directly in the backing list for the ListView and have the ListView display them OK. Otherwise a toString is called on the item to set the item's text (this is the case which is occurring for our simple example of Strings in the backing list).
    Now the important thing to note about the ListCell implementation is that the clever logic of translating the backing item for the cell to a visual representation is occurring in an updateItem call. This updateItem method is invoked by the JavaFX system on the ListCell whenever the backing item for the cell has been invalidated, for example the item has been edited, a new item added, or the items in the list have been reordered.
    So when somebody presses, the "Add Guava" button, a new ListCell is not created, instead updateItem is called on an already existing empty cell. This is because when we started the application, there was space for 17 rows, so 17 cells were already created, it is just that most of them were empty because we only had 3 items in the backing list for the ListView.
    Now, if we press one of the sort buttons to reorder the backing list, it will cause the existing list cells to become invalidated, and updateItem will be called on each of the cells according to the change permutations in the ObservableList. Note that as each item is updated, a new Labeled display node for the item is not created, instead the setText method is invoked which changes the text for the existing Labeled.
    There are a couple of extra cases to understand. Our backing list currently maxes out at 4 items. Let's say we drag the bottom of our stage up so that the available space for the ListView was made really small (e.g. only 2 rows high). In this case, you will two rows (cells) and a scrollbar you can use to scroll up and down. As you scroll up and down it seems that some rows are scrolling off the screen and some are scrolling on the screen. What is actually happening though is that the same two cells are remaining on screen and their contents being continually updated and replaced as backing items come in and out of view. This is the magic of how the ListView is able to achieve it's efficiency when dealing with potentially very large collections or collections where not all of the required data is available on the client at the current time. Instead of creating visual cells for all of the possible items which can be placed in the list, instead the ListView creates cells only for the visible items and updates the content of those cells on an as needed basis. This concept is known in the List Cell creators jargon as a Virtual Flow in a Virtualized control.
    OK, so that was a little more interesting, but there have been a lot of words so far, and no custom cell factory. This was partly on purpose - there is lot you can do with the default cell factory without needing to create your own custom cell factory.
    But sometimes you do actually want to create your own cell factory when you want fine control over the look or behaviour of the cells.
    Let's say you want to show each item in the list with a capitalized friendly name "Apple", "Orange" and "Pear" and an icon - a picture of the corresponding fruit. To do this you would create a cell factory - something that can produce the visual representation of these things from the corresponding data values.
    import javafx.application.Application;
    import javafx.collections.*;
    import javafx.scene.Scene;
    import javafx.scene.control.*;
    import javafx.scene.image.*;
    import javafx.scene.layout.*;
    import javafx.stage.Stage;
    import javafx.util.Callback;
    public class ListViewCustomCellFactorySample extends Application {
      ObservableMap<String, Image> iconMap = FXCollections.observableHashMap();
      @Override public void init() {
        iconMap.put(
          "apple", 
          new Image(
            "http://uhallnyu.files.wordpress.com/2011/11/green-apple.jpg",
            0, 32, true, true
        iconMap.put(
          "orange",
          new Image(
            "http://i.i.com.com/cnwk.1d/i/tim/2011/03/10/orange_iStock_000001331357X_540x405.jpg",
            0, 32, true, true
        iconMap.put(
          "pear",  
          new Image(
            "http://smoothiejuicerecipes.com/pear.jpg",
            0, 32, true, true
      @Override public void start(Stage stage) {
        final ListView<String> listView = new ListView<>();
        listView.setItems(FXCollections.observableArrayList("apple", "orange", "pear"));
        listView.setCellFactory(new Callback<ListView<String>, ListCell<String>>() {
          @Override public ListCell<String> call(ListView<String> stringListView) {
            return new LabeledIconListCell();
        VBox layout = new VBox(10);
        VBox.setVgrow(listView, Priority.ALWAYS);
        listView.setMinHeight(0);
        layout.getChildren().addAll(
            listView
        stage.setScene(new Scene(layout));
        stage.show();
      public static void main(String[] args) { launch(args); }
      private class LabeledIconListCell extends ListCell<String> {
        @Override protected void updateItem(String item, boolean empty) {
          super.updateItem(item, empty);
          if (item != null) {
            String friendlyText = item.toString();
            if (item.length() > 0) {
              friendlyText = item.substring(0, 1).toUpperCase() + item.substring(1);
            setText(friendlyText);
            setGraphic(
                StackPaneBuilder
                    .create()
                    .prefWidth(55)
                    .children(
                        new ImageView(
                            iconMap.get(item)
                    .build()
          } else {
            setText("");
            setGraphic(null);
    }Here what the cell factory has done is to check what value of the backing item for the cell is whenever that item has been updated, and set some customized label text and graphic representation for the cell.
    As a minor point, for efficiency, and because there are only a few of them, the required images are loaded and scaled up front so that they don't been to be reloaded every time the cell is updated with a different value (which if the image loading was within the cell's updateItem call could mean that the same image could potentially get loaded multiple times.
    My personal take on this is that it is powerful but complicated. Often people will gravitate towards using the complex ListView and TableView APIs when they don't necessarily need all of the functionality and virtualization efficiency capabilities that the virtualized controls offer. In many cases, simple layout mechanisms such VBoxes and Grids can be a better choice. However, if you have a need for the virtualized functions, then it's good to know that things like ListView and TableView are there if you can work out how to use them well in your case.
    Also note that JavaFX 2.2+ has numerous convenience methods for creating different kinds of cells which you may be able to use in standard cases to avoid some of the overhead in creating your own, for example the CheckBoxListCell, the ComboBoxListCell and the TextFieldListCell. And there are many more such simplifying higher level abstractions in the DataFX library.
    One other point worth observing is that if you have a list of mutatable objects, for example Person objects with a changable last name field, then you need to make the object an Observable object with an invalidation implementation if you want the updateItem call in the cell factory to be invoked automatically whenever the object is mutated.
    A cell factory and a cell value factory are different things, but that is probably a topic for a different post.
    I realize this was a round about and lengthy explanation - hopefully it served some purpose and helped to explain some of the mysteries of cell factories.
    http://docs.oracle.com/javafx/2/api/javafx/scene/control/Cell.html
    http://www.javafxdata.org
    http://docs.oracle.com/javafx/2/ui_controls/list-view.htm

  • Creating a new cell factory, how to bind to my object's property

    As near as I can tell, the javafx binding using observable values, alot like jgoodies and its not like SWT databinding or WPF binding.
    I was creating a cell factory for a TreeView. Just using a label to display the contents and calling toString, alot like the way it works now. However, I could not figure out to create a binding that would bind to a property on my domain object. Is there a way to specify the binding to the Label's text property so that whatever object that the cell's item's value has I can bind to a property that I specify on it e.g. the "name" property. But I could not see how to do that. Also, the only way I could figure out how to update the Label's value was from updateItem. I thought maybe I could even setup the binding in updateItem so that when the TreeItem's value changed at least it would automatically update the label binding, but the API did not seem to support that.
    What's the right coding pattern to use when using straight Java coding?
    I know in jgoodies I could do this using the PresentationModel approach or master-detail SWT or WPF with just specifying the property on the item's property that I want in WPF.
    public static class MyTreeCell extends TreeCell<Object> {
              Label label;
              public MyTreeCell() {
                   label = new Label();
                   setNode(label);
              @Override
              public void updateItem(TreeItem<Object> arg0, boolean arg1) {
                   if (arg0 != null && arg0.getValue() != null) {
                        System.out.println("New value: " + arg0.getValue());
                        label.setText(arg0.getValue().toString());
                   } else {
                        System.out.println("New value is null and this println is called alot, why is that?");
                   super.updateItem(arg0, arg1);
         }

    Well the presentation model thing worked fine and I have some machinery for the cell factory/cell item to obtain a tree cell based on the domain object type (a template/factory is placed into the properties in the scenegraph hierarchy). But its not smooth yet and the pattern does not quite translate well into javafx. Because the cell factory produces cells that could be used for a variety of domain object types, all the logic gets pushed down to the treecell subclass which makes it messy. Maybe this is where CSS selectors need to come in, you specify the class of a tree cell for a specific domain object type and you can set that at the root of the application so it cascades. I'll see if this approach works.
    Here's the code for the javafx version of jgoodies' presentation model, less the corner cases. This allows you to bind to a property and change the bean underneath that the property accesses. I'm not convinced that having properties has observable values directly on the objects is the right model for javafx because of the coupling to the actual object the property represents. Sometimes, you need to represent the property concept separate from the actual object instance. Maybe this already exists in the library.
          * An object binding object that creates object bindings based on property
          * names specified as strings. This is a convenience class. Generally, the
          * return values from <code>getProperty()</code> should be used for binding
          * not the factory itself. The object should be a domain object bean with
          * bean methods to get or set the value using java bean naming conventions.
          * When the bean itself changes, the properties fire to indicate that their
          * values may have changed and the observing object should update itself.
          * <p>
          * This only handles reading bean properties. Need to add set() logic.
          * <p>
          * TODO: Make this work better. Many corner cases to cover. Include PCL.
         public static class BeanBindingFactory<T> extends ObjectBinding<T> {
              T bean;
              Map<String, CaptiveObjectProperty> properties = new HashMap<String, CaptiveObjectProperty>();
              public Property getProperty(String property) {
                   if (property == null || property.isEmpty())
                        throw new IllegalArgumentException("Property cannot be null");
                   if (properties.containsKey(property))
                        return properties.get(property);
                   CaptiveObjectProperty p = new CaptiveObjectProperty(this, property);
                   properties.put(property, p);
                   return p;
              public void setBean(T bean) {
                   this.bean = bean;
                   for (CaptiveObjectProperty p : properties.values()) {
                        p.invalidate();
                   fireValueChangedEvent();
              public T getBean() {
                   return bean;
              @Override
              protected T computeValue() {
                   return bean;
               * Lazily get the method representing the property.
               * @author Mr. Java
               * @param <T>
              protected static class CaptiveObjectProperty<T> extends
                        ObjectPropertyBase<T> {
                   String property;
                   Method m;
                   BeanBindingFactory factory;
                   public CaptiveObjectProperty(BeanBindingFactory factory,
                             String property) {
                        this.property = property;
                        this.factory = factory;
                   @Override
                   public Object getBean() {
                        if (factory == null || factory.getBean() == null)
                             return null;
                        return factory.getBean();
                   @Override
                   public T getValue() {
                        if (m == null) {
                             m = getMethod();
                        if (m == null)
                             return null;
                        try {
                             Object rval = m.invoke(factory.getBean());
                             return (T) rval;
                        } catch (Exception e) {
                             e.printStackTrace();
                        return null;
                   @Override
                   public String getName() {
                        return property;
                    * Invalidate the method. Perhaps the bean changed to another object
                    * and we should find the method on the new object.
                   public void invalidate() {
                        m = null;
                        fireValueChangedEvent();
                   protected Method getMethod() {
                        if (factory == null || factory.getBean() == null)
                             return null;
                        String methodName = "get"
                                  + Character.toUpperCase(getName().charAt(0));
                        if (getName().length() > 1)
                             methodName += getName().substring(1);
                        try {
                             Method mtmp = factory.getBean().getClass()
                                       .getMethod(methodName, new Class<?>[0]);
                             return mtmp;
                        } catch (Exception e) {
                             e.printStackTrace();
                        return null;
         }

  • ChoiceBox cell factory?

    Is there any reason why ChoiceBox doesn't use the same cell factory approach used by list/table/tree? Unless I'm missing something (?) it looks like the intention is that we should just add our nodes (i.e. cells) directly to the list of items.
    This is a little odd for me, I would normally want to put my data elements (Beans or enums) in the ChoiceBox and have the renderer take care of the rest, just like I do with lists/tables/trees. In the current model I am having to iterate over my data items and create a custom cell for each one, then when something is selected, etc, I have to get the data item out of my custom cell. It all feels a tad awkward?
    Edit: actually adding nodes doesn't seem to work either? I've resorted to creating a wrapper class for my Bean that provides a toString that does my formatting. In this approach, I also lose my underscores in my text (in the popup only, the button bit seems fine) - I assume this is something to do with mnemonics but I have not turned these on and can't see a simple way to turn them off. This all seems a bit wrong, what am I missing?

    Here's a simple little ComboBox that should tie us over until Jonathan writes us a real one. It's very light on features, but the basics work. You can obviously just copy and edit this code directly to suit your needs.
    The only slightly fancy thing I've done is add a 'Cell' interface to it so you can put in your own custom cell renderer for the current item (the popup list uses a normal cell factory). Just implement ComboBox.Cell with your custom Node and then call setCurrentItemCell. In a better implementation you would have a shared factory between the list and the current item, but we need to leave something for Jonathan to impress us with when he provides his real one ;)
    A couple of issues:
    * Ideally the popupList would shrink to fit its contents until it reaches a certain height and then it would start scrolling. Currently it just pops up at its preferred size, which is not as pretty as it could be. Anyone got any ideas on doing this better?
    * The closeOnEscape setting of the popup doesn't seem to be working. I think perhaps the List is blocking the keyboard input. I put a work around in using an event filter, but this shouldn't be needed in a perfect world.
    * The selection listener stuff only triggers if the selection is changed (which makes sense), we need something more like onAction or onCellClicked or something that fires when the user clicks a cell regardless of whether the selection was changed or not. I've used the selection model but also added a little event filter to catch the case when we click the already selected value.
    ComboBox.java
    package com.zenjava.playground.combo;
    import javafx.beans.value.ChangeListener;
    import javafx.beans.value.ObservableValue;
    import javafx.collections.ObservableList;
    import javafx.event.ActionEvent;
    import javafx.event.Event;
    import javafx.event.EventHandler;
    import javafx.geometry.Bounds;
    import javafx.scene.Node;
    import javafx.scene.Parent;
    import javafx.scene.control.*;
    import javafx.scene.input.KeyCode;
    import javafx.scene.input.KeyEvent;
    import javafx.scene.input.MouseEvent;
    import javafx.scene.layout.BorderPane;
    import javafx.stage.Popup;
    import javafx.util.Callback;
    public class ComboBox<ItemType> extends BorderPane
        private ListView<ItemType> popupList;
        private Popup popup;
        private Cell<ItemType> currentItemCell;
        public ComboBox()
            popupList = new ListView<ItemType>();
            popupList.getSelectionModel().setSelectionMode(SelectionMode.SINGLE);
            popupList.getSelectionModel().selectedItemProperty().addListener(new ChangeListener<ItemType>()
                public void changed(ObservableValue<? extends ItemType> source, ItemType oldValue, ItemType newValue)
                    currentItemCell.updateItem(newValue);
                    popup.hide();
            // need to force escape key to close since default behaviour is not working
            popupList.addEventFilter(KeyEvent.KEY_PRESSED, new EventHandler<Event>()
                public void handle(Event event)
                    KeyEvent keyEvent = (KeyEvent) event;
                    if (KeyCode.ESCAPE.equals(keyEvent.getCode()))
                        popup.hide();
            // need to force hiding of list for case when current selection is re-selected
            popupList.addEventFilter(MouseEvent.MOUSE_RELEASED, new EventHandler<Event>()
                public void handle(Event event)
                    popup.hide();
            popup = new Popup();
            popup.getContent().add(popupList);
            popup.setAutoHide(true);
            popup.setAutoFix(true);
            popup.setHideOnEscape(true);
            // use your own style for this
            Button popupButton = new Button(">");
            popupButton.setOnAction(new EventHandler<ActionEvent>()
                public void handle(ActionEvent actionEvent)
                    showPopup();
            setRight(popupButton);
            setCurrentItemCell(new SimpleCell<ItemType>());
        public void setCurrentItemCell(Cell<ItemType> cell)
            currentItemCell = cell;
            Node node = currentItemCell.getNode();
            node.setOnMouseClicked(new EventHandler<Event>()
                public void handle(Event event)
                    showPopup();
            setCenter(node);
        public MultipleSelectionModel<ItemType> getSelectionModel()
            return popupList.getSelectionModel();
        public ObservableList<ItemType> getItems()
            return popupList.getItems();
        public void set(Callback<ListView<ItemType>, ListCell<ItemType>> cellFactory)
            popupList.setCellFactory(cellFactory);
        public void showPopup()
            Parent parent = getParent();
            Bounds childBounds = getBoundsInParent();
            Bounds parentBounds = parent.localToScene(parent.getBoundsInLocal());
            double layoutX = childBounds.getMinX()
                    + parentBounds.getMinX() + parent.getScene().getX() + parent.getScene().getWindow().getX();
            double layoutY = childBounds.getMaxY()
                    + parentBounds.getMinY() + parent.getScene().getY() + parent.getScene().getWindow().getY();
            popup.show(this, layoutX, layoutY);
        public static interface Cell<ItemType>
            Node getNode();
            void updateItem(ItemType item);
        public static class SimpleCell<ItemType> extends TextField implements Cell<ItemType>
            public SimpleCell()
                setEditable(false);
                setStyle("-fx-cursor: hand");
            public Node getNode()
                return this;
            public void updateItem(ItemType item)
                setText(item != null ? item.toString() : "");
    }And here's how you would use it:
    public void start(Stage stage) throws Exception
        FlowPane root = new FlowPane();
        root.setStyle("-fx-padding: 30");
        root.getChildren().add(new Label("Choose your destiny:"));
        ComboBox<String> combo = new ComboBox<String>();
        combo.setStyle("-fx-border-color: black; -fx-border-width: 1");
        combo.getItems().addAll("Make a difference", "Do no harm", "Start a Krispy Kreme franchise");
        combo.getSelectionModel().selectedItemProperty().addListener(new ChangeListener<Object>()
            public void changed(ObservableValue<? extends Object> source, Object oldValue, Object newValue)
                System.out.println("Your destiny: " + newValue);
        root.getChildren().add(combo);
        Scene scene = new Scene(root, 300, 200);
        stage.setScene(scene);
        stage.show();
    }

  • I have an IPad mini WiFi (not cellular) and an IPhone 5. I use the bluetooth connection between both devices when on the road. I downloaded a navigation system on my IPad using GPS positioning. Is Bluetooth OK to use GPS positioning on the IPad?

    Hi
    I have an IPad mini WiFi (not cellular) and an IPhone 5. I use the bluetooth connection between both devices when on the road. I downloaded a navigation system on my IPad using GPS positioning. Is the Bluetooth connection working to use GPS positioning on the IPad using IPhone 5 as the hotspot?
    Thanks for your input
    Felix013

    try a RESET ALL SETTINGS

  • Tree in FXML (via cell factory)

    Hi,
    I am trying to create a tree in FXML, but I can't figure out how the event handling works.
    I know I need to add a cell factory and add the event handlers to the cells (since tree items don't have mouse events), but how can I
    create the cells in FXML?
    It seems I can add the cellFactory directly to the TreeView, since this code runs okay:
              <TreeView>
              <cellFactory></cellFactory>
                   <root>
                        <TreeItem value="root">
                             <children>
                                  <TreeItem value="c0">
                                       <children>
                                            <TreeItem value="c0topic0"></TreeItem>
                                            <TreeItem value="c0topic1"></TreeItem>
                                            <TreeItem value="c0topic2"></TreeItem>
                                            <TreeItem value="c0topic3"></TreeItem>                                        
                                       </children>
                                  </TreeItem>
                                  <TreeItem value="c1">
                                       <children>
                                            <TreeItem value="c1topic0"></TreeItem>
                                            <TreeItem value="c1topic1"></TreeItem>
                                            <TreeItem value="c1topic2"></TreeItem>                                        
                                       </children>                              
                                  </TreeItem>
                                  <TreeItem value="c2">
                                       <children>
                                            <TreeItem value="c2topic0"></TreeItem>
                                            <TreeItem value="c2topic1"></TreeItem>
                                            <TreeItem value="c2topic2"></TreeItem>
                                       </children>                              
                                  </TreeItem>                                                            
                             </children>
                        </TreeItem>
                   </root>
              </TreeView>But I don't know how I can implement a call-method and I can't add cells to the TreeItems (error: no valid tag).
    Does anyone have an idea or has even already implemented a tree in FXML?
    Thanks,
    Sela

    <TreeView fx:id="treeview">
        <root>
            <TreeItem fx:id="triRoot" value="%triRoot" expanded="true">
                <children>
                   <TreeItem fx:id="triReader" value="%triReader" expanded="true">
                      <graphic>
                          <ImageView>
                              <image>
                       <Image url="@triReader.png"/>
                   </image>
                </ImageView>
           </graphic>                              
                 <children>
                    <TreeItem fx:id="triReaderTopic0" value="%triReaderTopic0"></TreeItem>
                    <TreeItem fx:id="triReaderTopic1" value="%triReaderTopic1"></TreeItem>
                 </children>
             </TreeItem>
             <TreeItem fx:id="cat0" value="%cat0" expanded="true">
                <graphic>
                <ImageView>
                    <image>
                        <Image url="@icon1.png"/>
                    </image>
                </ImageView>
                </graphic>                              
                <children>
                    <TreeItem fx:id="cat0topic0" value="%cat0topic0"></TreeItem>                                        
                    <TreeItem fx:id="cat0topic1" value="%cat0topic1"></TreeItem>                                        
                </children>
             </TreeItem>
             <TreeItem fx:id="cat1" value="%cat1" expanded="true">
                <graphic>
                   <ImageView>
               <image>
                     <Image url="@icon2.png"/>
               </image>
         </ImageView>
               </graphic>                              
              <children>
              <TreeItem fx:id="cat1topic0" value="%cat1topic0"></TreeItem>
              <TreeItem fx:id="cat1topic1" value="%cat1topic1"></TreeItem>
              <TreeItem fx:id="cat1topic2" value="%cat1topic2"></TreeItem>                                   
              </children>                              
           </TreeItem>
           <TreeItem value="%cat2" expanded="true">
               <graphic>
                   <ImageView>
                 <image>
                      <Image url="@icon3.png"/>
                 </image>
                   </ImageView>
                </graphic>
                <children>
               <TreeItem fx:id="cat2topic0" value="%cat2topic0"></TreeItem>                                   
               <TreeItem fx:id="cat2topic1" value="%cat2topic1"></TreeItem>
               <TreeItem fx:id="cat2topic2" value="%cat2topic2"></TreeItem>
                </children>                              
             </TreeItem>                                                            
          </children>
       </TreeItem>
      </root>
    </TreeView> Here is the updated example. Within the controller I don't get the ids (fx:id="cat2topic0"), so I have to use the values to identify the TreeItem that
    is clicked. That is possible but of course I don't like it at all because the values are only variables and I want to be able to change them in the property files
    without touching the java code. I need to get the ids within the event handler.
    treeview.setCellFactory(new Callback<TreeView<String>,TreeCell<String>>(){
    @Override
                public TreeCell<String> call(TreeView<String> p) {
                     final MyTreeCell mytreecell = new MyTreeCell(itemcount++);
                     System.out.println(""+mytreecell.getId());
                     mytreecell.setOnMouseClicked(new EventHandler<MouseEvent>() {
                         @Override
                         public void handle(MouseEvent t) {

  • Using numbers, how do I tell what formulas a cell is used in?

    Using numbers, how do I tell what formulas a cell is used in?

    I am not aware there is a dependency list.  Aside from using an Apple  script to create a list there is no way.

  • Are you aware of any software similar to ADSL Navigation Tools that can be used with in Mac?

    Are you aware of any software similar to ADSL Navigation Tools that can be used with in Mac?

    The popup message always warns to do a backup first since there is the potential of lost data if the upgrade fails.
    Sadly, your only option at this point is to restore and hope there is a backup stored from a previous sync.
    Backing up, Updating and Restoring
    http://support.apple.com/kb/HT1414
    Unable to Update or Restore
    http://support.apple.com/kb/HT1808

  • Engine test cell automation using labview

    I want to know the hardware details of my application(engine test cell automation using labview).
    Amit Amrutkar

    >> I want to know the hardware details of my application(engine test cell automation using labview).
    I have a feeling that that one of the following happened  :
    A. The "Post" button was clicked by mistake before the compilation was over.
    B. The OP wants to know the hardware details for  his application which looks like an engine test cell automation. ( It thus must have been in a hardware forum I guess )
    Post more details on the number of analog channels , required resolution, sampling time etc and number of digital channels and there is a possiblity that we can start helping..
    Raghunathan
    LV2012 to Automate Hydraulic Test rigs.

  • Iterate a TableColumns cell factory

    How to iterate a cell factory of a table columns cell and change its alignment property at run time.
    Thanks.

    How to iterate a cell factory of a table columns cell and change its alignment propertyI don't understand this question. A CellFactory doesn't have an alignment. A CellFactory produces Cells. Cells can be aligned, but not CellFactories.
    Please describe what are you trying to accomplish (preferably without mention of factory), for example, user clicks on a button and sees <insert text here> happen.
    How to iterate the cell factories of a table:
    for (TableColumn c: table.getColumns()) {
      Callback cellFactory = c.getCellFactory();
      System.out.println(cellFactory);
    }

  • JavaFX 2.1 TableView that includes WebView cells

    I want to create a JavaFX table that, in the cells of one column, allows the user to edit XHTML text. I only need very basic formatting capabilities like bold, italic, striketrough.
    I have already managed to implement this by using my own subclass of TableCell and using a WebView for each cell (HTMLEditor would of course have been another choice, but my guess is that for my requirements, WebView should be sufficient).
    However, to make editing comfortable for the user, I need the following feature: the cell height needs to resize if the user enters multi-line text. .
    I had some ideas I have tried out, like using the loadContent method, creating an event handler in javascript, and setting the preferred size of the cell in it.
    I got none of my ideas to work properly, so I am stuck.
    Has anybody been successful in implementing something similar ?
    What I hope for is a code sample that implements this feature or parts of it.

    Have you tried 2.2?
    Add a style that reverts the color back to the caspian default:
    #myTable .table-cell {
        -fx-text-fill: -fx-text-inner-color;
    }By the way, this.getTableRow().getStyleClass().remove("triggerHighLight .table-cell") will not work because the styleClass property is a List<String> (technically and ObservableList<String>) so you need to remove each styleClass individually.
        this.getTableRow().getStyleClass().remove("triggerHighLight");
        this.getTableRow().getStyleClass().remove("table-cell");
        But then, you really don't want to remove the table-cell styleClass.

Maybe you are looking for

  • How to export security settings from Acrobat Pro

    I'm transferring my Acrobat Pro to a new computer.  Is there a way to export the security settings (passwords) that I have stored and then import them into Acrobat Pro on my new computer? Thanks, Steve

  • How many types of reports we can see in BI..?

    Hi I am new to BI How many types of reports we can see in BI..? I got some here like 1) COPA reports 2) Costbased reports 3) Artist p& L 4) HMF test...export active sheet....export shole wb..                       Upload PABEL NPS... i wanted to know

  • Script to Migrate AD

    Hello, I would like to know if it is possible to migrate the on-premise Active Directory to Azure with the help of Powershell script. I have seen the tools like ADConnect and DirSync but i would like to develop a script to accomplish that task. So i

  • Mac OS X Mavericks not allowing me to download Dreamweaver 11.0.2 Updater?

    The support thread here http://forums.adobe.com/thread/629224 says that the issue of Dreamweaver CS5 not opening in Mavericks has been fixed with this updater. However my computer is not allowing me to download this Updater because it is from an unid

  • IDT High Definition Audio CODEC (No Sound)

    i have the same issue but with a HP Elitebook 2540p running Windows 7 64bit. any advice? I tried to install the same driver you suggested above but it doesn't work thanks