I am using the linked hashmap to populate values in expandable list .I successfully populate them. Here key is the menuitems and values are corresponding modifiers I places two buttons foe increasing and decreasing quantity of menu items .As it is the key I remove them and update them and again I put them in the list. This time they are inserting on the lastrow . How to placethem in same position as they were before deletion?
The function where i update my key.
public void putminusquantity(int pos)
{
try
{
SaleDetailsMenuItems aa = (SaleDetailsMenuItems)listDataChild.keySet().toArray()[pos];
List<ModifList> modlist =listDataChild.get(aa);
//modlist.add(mli);
listDataChild.remove(aa);
int qty = Integer.parseInt(aa.getQuantity());
float priced = Float.parseFloat(aa.getPrice());
//Double finaltotal1 = Math.round( priced * 100.0 ) / 100.0;
//Toast.makeText(getApplicationContext(), finaltotal1.toString(), Toast.LENGTH_SHORT).show();
System.out.println(qty);
float priced1 = priced / qty;
if(qty>1)
{
qty--;
priced = priced1 * qty;
String quantity1 = Integer.toString(qty);
String price1 = Float.toString(priced);
aa.setQuantity(quantity1);
aa.setPrice(price1);
listDataChild.put(aa, modlist);
listviewAdapter = new ExpandableListAdapter(getApplicationContext(), listDataChild);
list.setAdapter(listviewAdapter);
listviewAdapter.notifyDataSetChanged();
resetquantity();
settotal();
}
else
{
Toast.makeText(getApplicationContext(), "Invalid Quantity", Toast.LENGTH_SHORT).show();
}
}
catch(Exception e)
{
System.out.println(e);
}
}
Here is the model class:
class SaleDetailsMenuItems extends Sale
{
int i;
private int id;
private String name;
private String price;
private String quantity;
private int statuss;
private String itemnote;
private long saledetailId;
private long saleid;
private int menutype;
private long menu_id;
private int istaxinclusive;
private int coursing_id;
private String seatname;
private int seatId;
private String reason;
// private int discountdtls;
private int istaxexmpt;
private float taxpercent;
//private float inctaxpercent;
private float taxamt;
private float incltaxamt;
private int ordertype;
private boolean istaxincl;
private int storeid;
private int crtdby;
private int modby;
private int status;
public SaleDetailsMenuItems(int i1,String item, String quantity,
String price, int id, int statuss,String itemnote)
{
// TODO Auto-generated constructor stub
this.i=i1;
this.id=id;
this.name = item;
this.quantity = quantity;
this.price = price;
this.statuss = statuss;
this.itemnote = itemnote;
//this.flag = flag;
}
public int getStatuss() {
return statuss;
}
public void setStatuss(int statuss) {
this.statuss = statuss;
}
public long getSaledetailId() {
return saledetailId;
}
public void setSaledetailId(long saledetailId) {
this.saledetailId = saledetailId;
}
public long getSaleid() {
return saleid;
}
public void setSaleid(long saleid) {
this.saleid = saleid;
}
public int getMenutype() {
return menutype;
}
public void setMenutype(int menutype) {
this.menutype = menutype;
}
public long getMenu_id() {
return menu_id;
}
public void setMenu_id(long menu_id) {
this.menu_id = menu_id;
}
public int getIstaxinclusive() {
return istaxinclusive;
}
public void setIstaxinclusive(int istaxinclusive) {
this.istaxinclusive = istaxinclusive;
}
public int getCoursing_id() {
return coursing_id;
}
public void setCoursing_id(int coursing_id) {
this.coursing_id = coursing_id;
}
public String getSeatname() {
return seatname;
}
public void setSeatname(String seatname) {
this.seatname = seatname;
}
public int getSeatId() {
return seatId;
}
public void setSeatId(int seatId) {
this.seatId = seatId;
}
public String getReason() {
return reason;
}
public void setReason(String reason) {
this.reason = reason;
}
public int getIstaxexmpt() {
return istaxexmpt;
}
public void setIstaxexmpt(int istaxexmpt) {
this.istaxexmpt = istaxexmpt;
}
public float getTaxpercent() {
return taxpercent;
}
public void setTaxpercent(float taxpercent) {
this.taxpercent = taxpercent;
}
public float getTaxamt() {
return taxamt;
}
public void setTaxamt(float taxamt) {
this.taxamt = taxamt;
}
public float getIncltaxamt() {
return incltaxamt;
}
public void setIncltaxamt(float incltaxamt) {
this.incltaxamt = incltaxamt;
}
public int getOrdertype() {
return ordertype;
}
public void setOrdertype(int ordertype) {
this.ordertype = ordertype;
}
public boolean isIstaxincl() {
return istaxincl;
}
public void setIstaxincl(boolean istaxincl) {
this.istaxincl = istaxincl;
}
public int getStoreid() {
return storeid;
}
public void setStoreid(int storeid) {
this.storeid = storeid;
}
public int getCrtdby() {
return crtdby;
}
public void setCrtdby(int crtdby) {
this.crtdby = crtdby;
}
public int getModby() {
return modby;
}
public void setModby(int modby) {
this.modby = modby;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getPrice() {
return price;
}
public void setPrice(String price) {
this.price = price;
}
public String getQuantity() {
return quantity;
}
public void setQuantity(String quantity) {
this.quantity = quantity;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public int getStatus() {
return statuss;
}
public void setStatus(int statuss) {
this.statuss = statuss;
}
public String getItemnote() {
return itemnote;
}
public void setItemnote(String itemnote) {
this.itemnote = itemnote;
}
} I am using this class's object as key in my Map.
TreeMap
Is the way to sort the map by key. May be this will help you
Using this example I want to create TreeView with Nodes that I can drag in order to change their position.
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
import javafx.application.Application;
import javafx.event.EventHandler;
import javafx.scene.Scene;
import javafx.scene.control.TreeCell;
import javafx.scene.control.TreeItem;
import javafx.scene.control.TreeItem.TreeModificationEvent;
import javafx.scene.control.TreeView;
import javafx.scene.input.ClipboardContent;
import javafx.scene.input.DataFormat;
import javafx.scene.input.DragEvent;
import javafx.scene.input.Dragboard;
import javafx.scene.input.MouseEvent;
import javafx.scene.input.TransferMode;
import javafx.scene.layout.VBox;
import javafx.stage.Stage;
import javafx.util.Callback;
public class MainApp extends Application {
private EventHandler<TreeModificationEvent<DynamicTreeNodeModel>> branchExpandedEventHandler;
/**
* #param args the command line arguments
*/
public static void main(String[] args) {
Application.launch(MainApp.class, args);
}
#Override
public void start(Stage primaryStage) {
primaryStage.setTitle("Example Dynamic Tree");
primaryStage.setResizable(true);
final VBox box = new VBox();
box.setFillWidth(false);
Scene scene = new Scene(box);
primaryStage.setScene(scene);
box.getChildren().add(this.getExampleTree());
primaryStage.show();
}
private TreeView<DynamicTreeNodeModel> getExampleTree() {
DynamicTreeNodeModel rootNode = new RandomDynamicTreeNodeModel(null, "Root Node");
TreeView<DynamicTreeNodeModel> treeView = new TreeView<DynamicTreeNodeModel>();
treeView.setCellFactory(new Callback<TreeView<DynamicTreeNodeModel>, TreeCell<DynamicTreeNodeModel>>() {
#Override
public TreeCell call(TreeView<DynamicTreeNodeModel> param) {
return new DnDCell(param);
}
});
treeView.setPrefSize(1000, 750);
TreeItem rootItem = new TreeItem(rootNode);
branchExpandedEventHandler = new EventHandler<TreeModificationEvent<DynamicTreeNodeModel>>() {
public void handle(TreeModificationEvent<DynamicTreeNodeModel> event) {
// System.out.println("handling event " + event);
TreeItem<DynamicTreeNodeModel> item = event.getTreeItem();
populateTreeItem(item);
}
};
rootItem.addEventHandler(TreeItem.branchExpandedEvent(), branchExpandedEventHandler);
treeView.setShowRoot(true);
treeView.setRoot(rootItem);
populateTreeItem(rootItem);
rootItem.setExpanded(true);
// treeView.setCellFactory(new LearningTreeCellFactory());
return treeView;
}
private void populateTreeItem(TreeItem<DynamicTreeNodeModel> item) {
DynamicTreeNodeModel node = item.getValue();
boolean isPopulated = node.isPopulated();
boolean areGrandChildrenPopulated = node.areChildenPopulated();
node.populateToDepth(2);
if (!isPopulated) {
for (DynamicTreeNodeModel childNode : node.getChildren()) {
TreeItem childItem = new TreeItem(childNode);
childItem.addEventHandler(TreeItem.branchExpandedEvent(), branchExpandedEventHandler);
item.getChildren().add(childItem);
}
}
if (!areGrandChildrenPopulated) {
int i = 0;
for (TreeItem childItem : item.getChildren()) {
// get cooresponding node in the model
DynamicTreeNodeModel childNode = node.getChildren().get(i);
i++;
for (DynamicTreeNodeModel grandChildNode : childNode.getChildren()) {
TreeItem grandChildItem = new TreeItem(grandChildNode);
grandChildItem.addEventHandler(TreeItem.branchExpandedEvent(), branchExpandedEventHandler);
childItem.getChildren().add(grandChildItem);
}
}
}
}
private static interface DynamicTreeNodeModel {
public String getName();
public void setName(String name);
public boolean isPopulated();
public boolean areChildenPopulated();
public List<DynamicTreeNodeModel> getChildren();
public void setChildren(List<DynamicTreeNodeModel> children);
public DynamicTreeNodeModel getParent();
public void setParent(DynamicTreeNodeModel parent);
public void populateToDepth(int depth);
#Override
public String toString();
}
private static class RandomDynamicTreeNodeModel implements DynamicTreeNodeModel {
private DynamicTreeNodeModel parent;
private String name;
private List<DynamicTreeNodeModel> children = null;
public RandomDynamicTreeNodeModel(DynamicTreeNodeModel parent, String name) {
this.parent = parent;
this.name = name;
}
#Override
public String getName() {
return name;
}
#Override
public void setName(String name) {
this.name = name;
}
#Override
public boolean isPopulated() {
if (children == null) {
return false;
}
return true;
}
#Override
public boolean areChildenPopulated() {
if (!this.isPopulated()) {
return false;
}
for (DynamicTreeNodeModel child : this.children) {
if (!child.isPopulated()) {
return false;
}
}
return true;
}
#Override
public List<DynamicTreeNodeModel> getChildren() {
return children;
}
#Override
public void setChildren(List<DynamicTreeNodeModel> children) {
this.children = children;
}
#Override
public DynamicTreeNodeModel getParent() {
return parent;
}
#Override
public void setParent(DynamicTreeNodeModel parent) {
this.parent = parent;
}
private static Random random = new Random();
#Override
public void populateToDepth(int depth) {
if (depth <= 0) {
return;
}
if (children == null) {
int num = random.nextInt(5);
System.out.println("got a random number " + num);
children = new ArrayList(num);
for (int i = 0; i < num; i++) {
children.add(new RandomDynamicTreeNodeModel(this, "child " + i));
}
}
int childDepth = depth - 1;
for (DynamicTreeNodeModel child : children) {
child.populateToDepth(childDepth);
}
}
#Override
public String toString() {
return this.name;
}
}
public class DnDCell extends TreeCell<DynamicTreeNodeModel> {
private TreeView<DynamicTreeNodeModel> parentTree;
public DnDCell(final TreeView<DynamicTreeNodeModel> parentTree) {
this.parentTree = parentTree;
// ON SOURCE NODE.
setOnDragDetected(new EventHandler<MouseEvent>() {
#Override
public void handle(MouseEvent event) {
System.out.println("Drag detected on " + item);
if (item == null) {
return;
}
Dragboard dragBoard = startDragAndDrop(TransferMode.MOVE);
ClipboardContent content = new ClipboardContent();
content.put(DataFormat.PLAIN_TEXT, item.toString());
dragBoard.setContent(content);
event.consume();
}
});
setOnDragDone(new EventHandler<DragEvent>() {
#Override
public void handle(DragEvent dragEvent) {
System.out.println("Drag done on " + item);
dragEvent.consume();
}
});
// ON TARGET NODE.
// setOnDragEntered(new EventHandler<DragEvent>() {
// #Override
// public void handle(DragEvent dragEvent) {
// System.out.println("Drag entered on " + item);
// dragEvent.consume();
// }
// });
setOnDragOver(new EventHandler<DragEvent>() {
#Override
public void handle(DragEvent dragEvent) {
System.out.println("Drag over on " + item);
if (dragEvent.getDragboard().hasString()) {
int valueToMove = Integer.parseInt(dragEvent.getDragboard().getString());
if (valueToMove != item) {
// We accept the transfer!!!!!
dragEvent.acceptTransferModes(TransferMode.MOVE);
}
}
dragEvent.consume();
}
});
// setOnDragExited(new EventHandler<DragEvent>() {
// #Override
// public void handle(DragEvent dragEvent) {
// System.out.println("Drag exited on " + item);
// dragEvent.consume();
// }
// });
setOnDragDropped(new EventHandler<DragEvent>() {
#Override
public void handle(DragEvent dragEvent) {
System.out.println("Drag dropped on " + item);
int valueToMove = Integer.parseInt(dragEvent.getDragboard().getString());
TreeItem<DynamicTreeNodeModel> itemToMove = search(parentTree.getRoot(), valueToMove);
TreeItem<DynamicTreeNodeModel> newParent = search(parentTree.getRoot(), item);
// Remove from former parent.
itemToMove.getParent().getChildren().remove(itemToMove);
// Add to new parent.
newParent.getChildren().add(itemToMove);
newParent.setExpanded(true);
dragEvent.consume();
}
});
}
private TreeItem<DynamicTreeNodeModel> search(final TreeItem<DynamicTreeNodeModel> currentNode, final int valueToSearch) {
TreeItem<DynamicTreeNodeModel> result = null;
if (currentNode.getValue() == valueToSearch) {
result = currentNode;
} else if (!currentNode.isLeaf()) {
for (TreeItem<DynamicTreeNodeModel> child : currentNode.getChildren()) {
result = search(child, valueToSearch);
if (result != null) {
break;
}
}
}
return result;
}
private DynamicTreeNodeModel item;
#Override
protected void updateItem(DynamicTreeNodeModel item, boolean empty) {
super.updateItem(item, empty);
this.item = item;
String text = (item == null) ? null : item.toString();
setText(text);
}
}
}
I tried to implement the example but I'm facing a problem here:
#Controller
public class FileUploadController {
if (valueToMove != item) {
// We accept the transfer!!!!!
dragEvent.acceptTransferModes(TransferMode.MOVE);
}
...............
if (currentNode.getValue() == valueToSearch) {
I'm getting incomparable types: DynamicTreeNodeModel and int
Can you help me to fix this issue?
please try this:
/*
* To change this license header, choose License Headers in Project Properties.
* To change this template file, choose Tools | Templates
* and open the template in the editor.
*/
package test;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
import java.util.logging.Level;
import java.util.logging.Logger;
import javafx.application.Application;
import javafx.event.EventHandler;
import javafx.scene.Scene;
import javafx.scene.control.TreeCell;
import javafx.scene.control.TreeItem;
import javafx.scene.control.TreeItem.TreeModificationEvent;
import javafx.scene.control.TreeView;
import javafx.scene.input.ClipboardContent;
import javafx.scene.input.DataFormat;
import javafx.scene.input.DragEvent;
import javafx.scene.input.Dragboard;
import javafx.scene.input.MouseEvent;
import javafx.scene.input.TransferMode;
import javafx.scene.layout.VBox;
import javafx.stage.Stage;
import javafx.util.Callback;
public class MainApp extends Application {
private EventHandler<TreeModificationEvent<DynamicTreeNodeModel>> branchExpandedEventHandler;
/**
* #param args the command line arguments
*/
public static void main(String[] args) {
Application.launch(MainApp.class, args);
}
#Override
public void start(Stage primaryStage) {
primaryStage.setTitle("Example Dynamic Tree");
primaryStage.setResizable(true);
final VBox box = new VBox();
box.setFillWidth(false);
Scene scene = new Scene(box);
primaryStage.setScene(scene);
box.getChildren().add(this.getExampleTree());
primaryStage.show();
}
private TreeView<DynamicTreeNodeModel> getExampleTree() {
DynamicTreeNodeModel rootNode = new RandomDynamicTreeNodeModel(null, "Root Node");
TreeView<DynamicTreeNodeModel> treeView = new TreeView<DynamicTreeNodeModel>();
treeView.setCellFactory(new Callback<TreeView<DynamicTreeNodeModel>, TreeCell<DynamicTreeNodeModel>>() {
#Override
public TreeCell call(TreeView<DynamicTreeNodeModel> param) {
return new DnDCell(param);
}
});
treeView.setPrefSize(1000, 750);
TreeItem rootItem = new TreeItem(rootNode);
branchExpandedEventHandler = new EventHandler<TreeModificationEvent<DynamicTreeNodeModel>>() {
public void handle(TreeModificationEvent<DynamicTreeNodeModel> event) {
// System.out.println("handling event " + event);
TreeItem<DynamicTreeNodeModel> item = event.getTreeItem();
populateTreeItem(item);
}
};
rootItem.addEventHandler(TreeItem.branchExpandedEvent(), branchExpandedEventHandler);
treeView.setShowRoot(true);
treeView.setRoot(rootItem);
populateTreeItem(rootItem);
rootItem.setExpanded(true);
// treeView.setCellFactory(new LearningTreeCellFactory());
return treeView;
}
private void populateTreeItem(TreeItem<DynamicTreeNodeModel> item) {
DynamicTreeNodeModel node = item.getValue();
boolean isPopulated = node.isPopulated();
boolean areGrandChildrenPopulated = node.areChildenPopulated();
node.populateToDepth(2);
if (!isPopulated) {
for (DynamicTreeNodeModel childNode : node.getChildren()) {
TreeItem childItem = new TreeItem(childNode);
childItem.addEventHandler(TreeItem.branchExpandedEvent(), branchExpandedEventHandler);
item.getChildren().add(childItem);
}
}
if (!areGrandChildrenPopulated) {
int i = 0;
int size = node.getChildren().size();
for (TreeItem childItem : item.getChildren()) {
// get cooresponding node in the model
if (i < size) {
DynamicTreeNodeModel childNode = node.getChildren().get(i);
i++;
for (DynamicTreeNodeModel grandChildNode : childNode.getChildren()) {
TreeItem grandChildItem = new TreeItem(grandChildNode);
grandChildItem.addEventHandler(TreeItem.branchExpandedEvent(), branchExpandedEventHandler);
childItem.getChildren().add(grandChildItem);
}
}
}
}
}
private static interface DynamicTreeNodeModel {
public String getName();
public void setName(String name);
public boolean isPopulated();
public boolean areChildenPopulated();
public List<DynamicTreeNodeModel> getChildren();
public void setChildren(List<DynamicTreeNodeModel> children);
public DynamicTreeNodeModel getParent();
public void setParent(DynamicTreeNodeModel parent);
public void populateToDepth(int depth);
#Override
public String toString();
}
private static class RandomDynamicTreeNodeModel implements DynamicTreeNodeModel {
private DynamicTreeNodeModel parent;
private String name;
private List<DynamicTreeNodeModel> children = null;
public RandomDynamicTreeNodeModel(DynamicTreeNodeModel parent, String name) {
this.parent = parent;
this.name = name;
}
#Override
public String getName() {
return name;
}
#Override
public void setName(String name) {
this.name = name;
}
#Override
public boolean isPopulated() {
if (children == null) {
return false;
}
return true;
}
#Override
public boolean areChildenPopulated() {
if (!this.isPopulated()) {
return false;
}
for (DynamicTreeNodeModel child : this.children) {
if (!child.isPopulated()) {
return false;
}
}
return true;
}
#Override
public List<DynamicTreeNodeModel> getChildren() {
return children;
}
#Override
public void setChildren(List<DynamicTreeNodeModel> children) {
this.children = children;
}
#Override
public DynamicTreeNodeModel getParent() {
return parent;
}
#Override
public void setParent(DynamicTreeNodeModel parent) {
this.parent = parent;
}
private static Random random = new Random();
#Override
public void populateToDepth(int depth) {
if (depth <= 0) {
return;
}
if (children == null) {
int num = random.nextInt(5);
System.out.println("got a random number " + num);
children = new ArrayList(num);
for (int i = 0; i < num; i++) {
// children.add(new RandomDynamicTreeNodeModel(this, "child " + i));
children.add(new RandomDynamicTreeNodeModel(this, "child " + System.currentTimeMillis()));
try {
Thread.sleep(100);
} catch (InterruptedException ex) {
Logger.getLogger(MainApp.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
int childDepth = depth - 1;
for (DynamicTreeNodeModel child : children) {
child.populateToDepth(childDepth);
}
}
#Override
public String toString() {
return this.name;
}
}
public class DnDCell extends TreeCell<DynamicTreeNodeModel> {
private TreeView<DynamicTreeNodeModel> parentTree;
public DnDCell(final TreeView<DynamicTreeNodeModel> parentTree) {
this.parentTree = parentTree;
// ON SOURCE NODE.
setOnDragDetected(new EventHandler<MouseEvent>() {
#Override
public void handle(MouseEvent event) {
System.out.println("Drag detected on " + item);
if (item == null) {
return;
}
Dragboard dragBoard = startDragAndDrop(TransferMode.MOVE);
ClipboardContent content = new ClipboardContent();
content.put(DataFormat.PLAIN_TEXT, item.toString());
dragBoard.setContent(content);
event.consume();
}
});
setOnDragDone(new EventHandler<DragEvent>() {
#Override
public void handle(DragEvent dragEvent) {
System.out.println("Drag done on " + item);
dragEvent.consume();
}
});
// ON TARGET NODE.
// setOnDragEntered(new EventHandler<DragEvent>() {
// #Override
// public void handle(DragEvent dragEvent) {
// System.out.println("Drag entered on " + item);
// dragEvent.consume();
// }
// });
setOnDragOver(new EventHandler<DragEvent>() {
#Override
public void handle(DragEvent dragEvent) {
System.out.println("Drag over on " + item);
if (dragEvent.getDragboard().hasString()) {
String valueToMove = dragEvent.getDragboard().getString();
if (!valueToMove.matches(item.getName())) {
// We accept the transfer!!!!!
dragEvent.acceptTransferModes(TransferMode.MOVE);
}
}
dragEvent.consume();
}
});
// setOnDragExited(new EventHandler<DragEvent>() {
// #Override
// public void handle(DragEvent dragEvent) {
// System.out.println("Drag exited on " + item);
// dragEvent.consume();
// }
// });
setOnDragDropped(new EventHandler<DragEvent>() {
#Override
public void handle(DragEvent dragEvent) {
System.out.println("Drag dropped on " + item);
String valueToMove = dragEvent.getDragboard().getString();
TreeItem<DynamicTreeNodeModel> itemToMove = search(parentTree.getRoot(), valueToMove);
TreeItem<DynamicTreeNodeModel> newParent = search(parentTree.getRoot(), item.getName());
// Remove from former parent.
itemToMove.getParent().getChildren().remove(itemToMove);
// Add to new parent.
newParent.getChildren().add(itemToMove);
newParent.setExpanded(true);
dragEvent.consume();
}
});
}
private TreeItem<DynamicTreeNodeModel> search(final TreeItem<DynamicTreeNodeModel> currentNode, final String valueToSearch) {
TreeItem<DynamicTreeNodeModel> result = null;
if (currentNode.getValue().getName().matches(valueToSearch)) {
result = currentNode;
} else if (!currentNode.isLeaf()) {
for (TreeItem<DynamicTreeNodeModel> child : currentNode.getChildren()) {
result = search(child, valueToSearch);
if (result != null) {
break;
}
}
}
return result;
}
private DynamicTreeNodeModel item;
#Override
protected void updateItem(DynamicTreeNodeModel item, boolean empty) {
super.updateItem(item, empty);
this.item = item;
String text = (item == null) ? null : item.toString();
setText(text);
}
}
}
In here, I compare the names (same as Ithachi's opinion) and did some tweaks (check your populateTreeItem(..) function and modify it to suit your need - if currently it doesn't)..
to avoid duplicate names, I used system.currentTimemillis as part of the node's name..
hope it helps..
I want to use a TreeView to display categories and actual content. I used this tutorial to follow my example, since they do something similiar but they simplify it.
I have something like this
public class Category {
final StringProperty categoryName = new SimpleStringProperty();
final ListProperty<Contact> contactList = new SimpleListProperty<>(FXCollections.<Contact>observableArrayList());
public Category(String name, List<Contact> contactList) {
this.categoryName.set(name);
this.contactList.setAll(contactList);
}
public StringProperty categoryNameProperty() { return this.categoryName; }
public ListProperty<Contact> contactListProperty() { return this.contactList; }
}
public class Contact {
final StringProperty contactName = new SimpleStringProperty();
public Contact(String name) {
this.contactName.set(name);
}
public StringProperty contactNameProperty() { return this.contactName; }
}
And now I want to build a TreeView out of a List<Category> with the underlying contacts automatically inserted as child nodes. Is this possible? If possible I would like not modify the Model itself. I thought of extending TreeItem<T> but I am not sure how far this will get me.
Ok I solved this with this, somebody by change a better solution?
public class Main extends Application {
#Override
public void start(Stage stage) {
Scene scene = new Scene(new Group());
stage.setWidth(300);
stage.setHeight(500);
final TreeView<MailTreeItem> tree = new TreeView<>();
final List<Category> categoryList = FXCollections.observableArrayList();
tree.getSelectionModel().selectedItemProperty().addListener(new ChangeListener<TreeItem<MailTreeItem>>() {
#Override
public void changed(
ObservableValue<? extends TreeItem<MailTreeItem>> observable,
TreeItem<MailTreeItem> oldValue,
TreeItem<MailTreeItem> newValue) {
newValue.getValue();
}
});
final List<Contact> categoryContact1List = FXCollections.observableArrayList();
categoryContact1List.add(new Contact("Hans"));
categoryContact1List.add(new Contact("Dieter"));
final List<Contact> categoryContact2List = FXCollections.observableArrayList();
categoryContact2List.add(new Contact("Peter"));
categoryList.add(new Category("Freunde", categoryContact1List));
categoryList.add(new Category("Feinde", categoryContact2List));
final TreeItem<MailTreeItem> root = new TreeItem<MailTreeItem>(new RootTreeItem());
root.setExpanded(true);
tree.setRoot(root);
for (Category category : categoryList) {
final List<Contact> contactList = category.contactListProperty().get();
final TreeItem<MailTreeItem> categoryTreeItem = new TreeItem<MailTreeItem>(new CategoryTreeItem(category));
for (Contact contact : contactList) {
categoryTreeItem.getChildren().add(new TreeItem<MailTreeItem>(new ContactTreeItem(contact)));
}
root.getChildren().add(categoryTreeItem);
}
final VBox vbox = new VBox();
vbox.setSpacing(5);
vbox.setPadding(new Insets(10, 0, 0, 10));
vbox.getChildren().addAll(tree);
((Group) scene.getRoot()).getChildren().addAll(vbox);
stage.setScene(scene);
stage.show();
}
public static void main(String[] args) {
launch(args);
}
public interface MailTreeItem {
public boolean isCategory();
public boolean isContact();
public Category getCategory();
public Contact getContact();
}
public class RootTreeItem implements MailTreeItem {
#Override public String toString() { return "root"; }
#Override public boolean isCategory() { return false; }
#Override public boolean isContact() { return false; }
#Override public Category getCategory() { return null; }
#Override public Contact getContact() { return null; }
}
public class CategoryTreeItem implements MailTreeItem {
private ObjectProperty<Category> category = new SimpleObjectProperty<>();
public CategoryTreeItem(Category category) {
this.category.set(category);
}
public ObjectProperty<Category> categoryProperty() { return this.category; }
#Override public String toString() { return this.category.get().categoryNameProperty().get(); }
public boolean isCategory() { return true; }
public boolean isContact() { return false; }
public Category getCategory() { return this.category.get(); }
public Contact getContact() { return null; }
}
public class ContactTreeItem implements MailTreeItem {
private final ObjectProperty<Contact> contact = new SimpleObjectProperty<>();
public ContactTreeItem(Contact contact) {
this.contact.set(contact);
}
public ObjectProperty<Contact> contactProperty() { return this.contact; }
#Override public String toString() { return this.contact.get().contactNameProperty().get(); }
public boolean isCategory() { return false; }
public boolean isContact() { return true; }
public Category getCategory() { return null; }
public Contact getContact() { return this.contact.get(); }
}
public class Category {
private final StringProperty categoryName = new SimpleStringProperty();
private final ListProperty<Contact> contactList = new SimpleListProperty<>(FXCollections.<Contact>observableArrayList());
public Category(String name, List<Contact> contactList) {
this.categoryName.set(name);
this.contactList.setAll(contactList);
}
public StringProperty categoryNameProperty() { return this.categoryName; }
public ListProperty<Contact> contactListProperty() { return this.contactList; }
}
public class Contact {
private final StringProperty contactName = new SimpleStringProperty();
public Contact(String name) {
this.contactName.set(name);
}
public StringProperty contactNameProperty() { return this.contactName; }
}
}
First, let me discuss the data model :
I've compiled an HL7 definition in an tree-like object model, with 3 levels : Segment, Element and Subelement. The segment contains a List, and the Element contains a List. The relationship between those is kinda like "Continent-Country-City"
Second, i've created a GUI component composed of 3 combobox, each having a different ComboBoxModel accessing the object model described earlier.
I've applied the Observer pattern on the ComboBoxModel, so that each model is aware of which List<> it has to access :
- the HL7DefinitionElementModel observes the HL7DefinitionSegmentModel
- the HL7DefinitionSubelementModel observes the HL7DefinitionElementModel
When you pick a value in the first combobox (the Segment), the HL7DefinitionElementModel updates and store which Segment have been picked. The data is correctly stored. The first value is correctly displayed in the "closed" JComboBox.
But when you try to open that JComboBox (the Element), if the number of elements is too big (around 12), the items in the invoked Popup Menu are blank.
I'll gladly post any code.
I could send the entire project if needed, but haven't been able to reduce it to a SSCEE.
EDIT : here is an illustration of the problem
(http://imgur.com/AiJ8mu0)
EDIT : here is an SSCCE :
import java.awt.Dimension;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;
import java.util.Observable;
import java.util.Observer;
import java.util.Vector;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.event.ListDataListener;
public class Application extends JFrame {
/**
*
*/
private static final long serialVersionUID = -2517616123689799182L;
public Application() {
add(new HL7FieldSelector());
}
public static void main(String[] args) {
Application a = new Application();
a.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
a.setSize(new Dimension(400, 100));
a.setVisible(true);
}
}
class HL7FieldSelector extends JPanel implements ActionListener {
/**
*
*/
private static final long serialVersionUID = 6135074279269049773L;
private JComboBox<HL7DefinitionSegment> segment;
private JComboBox<HL7DefinitionElement> element;
private HL7DefinitionSegmentModel segmentModel;
private HL7DefinitionElementModel elementModel;
public HL7FieldSelector() {
segment = new JComboBox<HL7DefinitionSegment>();
element = new JComboBox<HL7DefinitionElement>();
segmentModel = new HL7DefinitionSegmentModel();
elementModel = new HL7DefinitionElementModel();
segmentModel.addObserver(elementModel);
segment.setModel(segmentModel);
element.setModel(elementModel);
segment.addActionListener(this);
element.addActionListener(this);
initUI();
}
private void initUI() {
this.setLayout(new GridLayout(1, 3));
this.add(segment);
this.add(element);
this.setMinimumSize(new Dimension(500, 30));
this.setPreferredSize(new Dimension(500, 30));
this.setMaximumSize(new Dimension(500, 30));
segment.setMaximumRowCount(10);
element.setMaximumRowCount(10);
}
#Override
public void actionPerformed(ActionEvent arg0) {
setVisible(!isVisible());
setVisible(!isVisible());
}
}
class HL7DefinitionSegment implements Comparable<HL7DefinitionSegment>, Serializable {
/**
*
*/
private static final long serialVersionUID = 7922798285885405647L;
private List<HL7DefinitionElement> elements;
private String name;
public HL7DefinitionSegment(String name, ArrayList<HL7DefinitionElement> elements) {
this.name = name;
this.elements = elements;
}
public HL7DefinitionSegment() {
elements = new Vector<HL7DefinitionElement>();
}
public boolean addElement(HL7DefinitionElement element) {
return elements.add(element);
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public List<HL7DefinitionElement> getElements() {
return elements;
}
#Override
public String toString() {
return this.name;
}
#Override
public int compareTo(HL7DefinitionSegment segment) {
return name.compareTo(segment.getName());
}
}
class HL7DefinitionElement implements Comparable<HL7DefinitionElement>, Serializable {
/**
*
*/
private static final long serialVersionUID = -5344721929162039227L;
private String name;
private String number;
public HL7DefinitionElement(String name, String number) {
this.name = name;
this.number = number;
}
public HL7DefinitionElement() {
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getNumber() {
return number;
}
public void setNumber(String number) {
this.number = number;
}
#Override
public String toString() {
return number + " " + name;
}
#Override
public int compareTo(HL7DefinitionElement element) {
return number.compareTo(element.getNumber());
}
}
class HL7DefinitionModel implements Serializable {
/**
*
*/
private static final long serialVersionUID = -8180582371776223436L;
private List<HL7DefinitionSegment> segments;
private static HL7DefinitionModel _instance;
public HL7DefinitionModel(Vector<HL7DefinitionSegment> segments) {
this.segments = segments;
}
public HL7DefinitionModel() {
segments = new Vector<HL7DefinitionSegment>();
}
public boolean addSegment(HL7DefinitionSegment segment) {
return segments.add(segment);
}
public List<HL7DefinitionSegment> getSegments() {
return segments;
}
public void setSegments(List<HL7DefinitionSegment> segments) {
this.segments = segments;
}
public static HL7DefinitionModel getInstance() {
if (_instance == null) {
_instance = new HL7DefinitionModel();
for (int i = 0; i < 2; i++) {
HL7DefinitionSegment s = new HL7DefinitionSegment();
s.setName("SEG" + i);
for (int j = 0; j < 20; j++) {
s.addElement(new HL7DefinitionElement("" + j + j + j, "" + j));
}
_instance.addSegment(s);
}
}
return _instance;
}
}
class HL7DefinitionSegmentModel extends Observable implements javax.swing.ComboBoxModel<HL7DefinitionSegment> {
private HL7DefinitionModel model;
private HL7DefinitionSegment selectedItem;
public HL7DefinitionSegmentModel() {
this.model = HL7DefinitionModel.getInstance();
this.selectedItem = getElementAt(0);
}
public void addListDataListener(ListDataListener l) {}
public void removeListDataListener(ListDataListener l) {}
#Override
public HL7DefinitionSegment getElementAt(int index) {
return model.getSegments().get(index);
}
#Override
public int getSize() {
return model.getSegments().size();
}
#Override
public Object getSelectedItem() {
return selectedItem;
}
#Override
public void setSelectedItem(Object anItem) {
this.selectedItem = (HL7DefinitionSegment) anItem;
setChanged();
notifyObservers();
}
}
class HL7DefinitionElementModel extends Observable implements javax.swing.ComboBoxModel<HL7DefinitionElement>, Observer {
private HL7DefinitionSegment segment;
private HL7DefinitionElement selectedItem;
public HL7DefinitionElementModel() {
this.segment = null;
}
#Override
public void update(Observable o, Object arg1) {
if (o instanceof HL7DefinitionSegmentModel) {
segment = (HL7DefinitionSegment) ((HL7DefinitionSegmentModel) o).getSelectedItem();
setSelectedItem(getElementAt(0));
}
}
public void addListDataListener(ListDataListener l) {}
public void removeListDataListener(ListDataListener l) {}
#Override
public HL7DefinitionElement getElementAt(final int index) {
return segment.getElements().get(index);
}
#Override
public int getSize() {
return (segment != null ? segment.getElements().size() : 0);
}
#Override
public Object getSelectedItem() {
return selectedItem;
}
#Override
public void setSelectedItem(Object anItem) {
this.selectedItem = (HL7DefinitionElement) anItem;
setChanged();
notifyObservers();
}
}
To reproduce the error :
- Launch the application
- Click on second combobox
- Click on the first, select option 2
- Click on second combobox
- Notice how the list is empty
if you do :
- Launch the application
- Click on the first combobox, select option 2
- Click on second combobox
- Notice how the list is populated
EDIT : Here is something else that I've found : The popup menu is only blank if there is more elements in it than in the initial "fill". That is, if the combobox is filled with 20 elements in the first pick, on the next picks the popup menu will be blank if the number of elements is 21 or more, displayed if the number of elements is 20 or less.
I've seen to hit a bump with this. I can't seem to get the array of the map from text file. I mean, I can get everything else BUT the map's array tiles.
This is the text file:
{
'name': 'map_one.txt',
'title': 'xxx One',
'currentMap': 4,
'rightMap': 3,
'lefttMap': 5,
'downMap': 1,
'upMap': 2,
'items': [
{ name: 'Pickaxe', x: 5, y: 1 },
{ name: 'Battleaxe', x: 2, y: 3 }
],
'map': [ [ 1,3,1,1,1,24,1,1,1,1,1,1,1 ],
[ 1,3,1,1,1,24,1,1,1,1,1,1,1 ],
[ 1,7,1,1,1,24,1,1,24,1,1,1,1 ],
[ 1,7,1,1,7,1,1,1,24,1,1,1,1 ],
[ 1,7,7,7,1,24,24,24,24,1,1,1,1 ],
[ 1,1,7,1,1,24,1,24,1,1,1,1,1 ],
[ 1,1,1,1,1,24,1,1,1,1,1,1,1 ],
[ 1,1,3,1,1,24,1,1,1,1,1,1,1 ],
[ 1,3,3,1,1,24,1,1,1,1,1,1,1 ]]
};
and when I run it, I get this:
==========================
JSON MAP LOAD...
==========================
Name of map: xxx One
File of map: map_one.txt
ID of map: 4
==========================
ITEMS IN MAP
==========================
# OF ITEMS: 2
>> Name: Pickaxe (5, 1)
>> Name: Battleaxe (2, 3)
==========================
TILES OF MAP
==========================
null
Press any key to continue . . .
See the null? It's *suppose to be numbers of arrays.
I'm doing it wrong, probably, I know. Here's what I have so far:
import java.util.*;
import java.io.*;
import com.google.gson.*;
public class readGoogle {
public static String MapTitle;
public static Data data;
public static Item item;
public static String dan;
public static FileReader fr;
public static int number;
public static int currentMap;
public static int tile;
public static String[] wepN;
public static void main(String[] args) {
try {
fr = new FileReader("map1.txt");
}catch(FileNotFoundException fne) {
fne.printStackTrace();
}
StringBuffer sb = new StringBuffer();
char[] b = new char[1000];
int n = 0;
try {
while ((n = fr.read(b)) > 0) {
sb.append(b, 0, n);
}
}catch(IOException rex) {
rex.printStackTrace();
}
String fileString = sb.toString();
try {
data = new Gson().fromJson(fileString, Data.class);
}catch (Exception er) {
er.printStackTrace();
}
System.out.println("==========================\n JSON MAP LOAD...\n==========================\n");
System.out.println("Name of map: " + data.getTitle());
System.out.println("File of map: " + data.getName());
System.out.println("ID of map: " + data.getCurrentMap());
String[] wepN = new String[100];
String[] wepX = new String[100];
String[] wepY = new String[100];
int[] tile = new int[256];
int wepQty = 0;
try {
for (int i=0; i < wepN.length; i++) {
if (data.getItems().get(i).getName() == null || "".equals(data.getItems().get(i).getName())) {
System.out.println(data.getItems().get(i).getName() + " -NO MOARE");
break;
}
wepN[i] = data.getItems().get(i).getName();
wepX[i] = Integer.toString(data.getItems().get(i).getX());
wepY[i] = Integer.toString(data.getItems().get(i).getY());
wepQty++;
}
}catch(Exception xe) { }
System.out.println("\n==========================\n ITEMS IN MAP\n==========================\n");
System.out.println("# OF ITEMS: " + wepQty + "\n");
for (int i=0; i < wepQty; i++) {
System.out.println(">> Name: " + wepN[i] + " (" + wepX[i] + ", " + wepY[i] + ")");
}
System.out.println("\n==========================\n TILES OF MAP\n==========================\n");
System.out.println(data.getMap());
}
public static class Item {
public String name;
public int x;
public int y;
public int tile;
public String getName() { return name; }
public int getX() { return x; }
public int getY() { return y; }
public void setName(String name) { this.name = name; }
public void setX(int x) { this.x = x; }
public void setY(int y) { this.y = y; }
}
public static class Data {
private String name;
private String title;
private int currentMap;
private List<Item> items;
private int[][] tile;
public String getName() { return name; }
public int getCurrentMap() { return currentMap; }
public String getTitle() { return title; }
public List<Item> getItems() { return items; }
public int[][] getMap() { return tile; }
public void setName(String name) { this.name = name; }
public void setTitle(String title) { this.title = title; }
public void setItems(List<Item> items) { this.items = items; }
public void setMap(int[][] tile) { this.tile = tile; }
}
}
My thought is that the Data class has a tiles field for holding the map but in the JSON it is named map.
try:
public static class Data {
private String name;
private String title;
private int currentMap;
private List<Item> items;
private int[][] map;
public String getName() { return name; }
public int getCurrentMap() { return currentMap; }
public String getTitle() { return title; }
public List<Item> getItems() { return items; }
public int[][] getMap() { return map; }
public void setName(String name) { this.name = name; }
public void setTitle(String title) { this.title = title; }
public void setItems(List<Item> items) { this.items = items; }
public void setMap(int[][] map) { this.map= map; }
}