Sure, I’ll show you what I think are the most important parts. And thanks for replying, @Krishna!
Okay, so here is the basic structure of the two main Java Beans:
public class Job {
// The variables this bean holds.
private Date shipDate;
private String jobId;
private String customerName;
private String customerPO;
private Timestamp proofSpecDate;
private Timestamp jobCompleted;
private PrintingCompany printingCompany;
private boolean overruns;
private List<OrderDetail> orderDetailList;
private boolean treeExpanded = true;
... (getters and setters) ...
}
public class OrderDetail {
// The variables this bean holds.
private int id;
private String orderId;
private String productId;
private String productDetail;
private PrintType printType;
private long numColors;
private long quantity;
private Timestamp itemCompleted;
private int proofNum;
private Timestamp proofDate;
private String thumbnail;
... (getters and setters) ...
}
As you can see, each Job bean contains a collection of OrderDetail beans. Sometimes, one Job will have only one OrderDetail, but sometimes it will have 2 or 3 or a dozen, etc. And the OrderDetail bean’s
orderId
matches the Job bean’s
jobId
to which it belongs. This forms the hierarchy that will be needed for the TreeTable.
Since it seems
SQLContainer
doesn’t implement
Container.Hierarchical
, and since I have yet to figure out any other
Container
class to use, I decided to just keep them as beans, they way they are in my desktop Swing application.
It may be terribly inefficient, but here’s how I’ve put them into a Vaadin TreeTable (this is in the main
init
method):
// Get a list of jobs on a particular date.
LocalDate tempDate = new LocalDate(2015, 7, 23);
List<Job> jobsList = null;
try {
jobsList = JobManager.getJobsByDate(tempDate);
} catch (SQLException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
if (jobsList != null) {
// As long as the list of Jobs isn't empty.
for (Job j : jobsList) {
// Go through each item in the Jobs list and add it
// (along with all of its OrderDetail items) to the TreeTable.
Object jobItemId;
CheckBox cbj = new CheckBox(j.getCustomerName(), j.getJobCompleted() != null);
cbj.addValueChangeListener(new ValueChangeListener() {
@Override
public void valueChange(ValueChangeEvent event) {
// TODO Auto-generated method stub
layout.addComponent(new Label("Job checkbox changed: " + cbj.getCaption() + ", value is now: " + event.getProperty().getValue()));
JobManager.jobClicked(event, j, treeTable);
}
});
jobItemId = treeTable.addItem(new Object{
userCanMarkAsDone ? cbj : j.getCustomerName(),
j.getJobId(), "", null, null, null}, j.getJobId());
logger.log(Level.INFO, "This Job's ItemID: " + jobItemId);
for (OrderDetail od : j.getOrderDetailList()) {
// Add each OrderDetail item to the TreeTable as well,
// and set their parent.
CheckBox cbod = new CheckBox(od.getProductId(), od.getItemCompleted() != null);
cbod.addValueChangeListener(new ValueChangeListener() {
@Override
public void valueChange(ValueChangeEvent event) {
// TODO Auto-generated method stub
layout.addComponent(new Label("OrderDetail checkbox changed: " + cbod.getCaption() + ", value is now: " + event.getProperty().getValue()));
layout.addComponent(new Label("Number of siblings: " + (j.getOrderDetailList().size() - 1)));
}
});
Object odItemId = treeTable.addItem(new Object{
userCanMarkAsDone ? cbod : od.getProductId(),
od.getProductDetail(), od.getPrintType().getValue(), od.getNumColors(), od.getQuantity(), (od.getNumColors() * od.getQuantity())}, od.getId());
treeTable.setParent(odItemId, jobItemId);
}
}
}
So each Job, then each Job’s OrderDetail gets added to the TreeTable. The key part is on line 24 in that last bit of code, which calls a method which will (hopefully) write to the bean and database whenever someone checks/unchecks a Job. (I’ll need to do the same for the OrderDetail part, too.) I think I can do that bit, but I also need it to check each of its children (OrderDetail) items. Here’s what I’ve got so far:
@SuppressWarnings("unchecked")
public static void jobClicked(ValueChangeEvent event, Job job, TreeTable treeTable) {
if ((boolean)event.getProperty().getValue()) {
logger.log(Level.INFO, "Job " + job.getJobId() + " checked, setting to timestamp: " + System.currentTimeMillis());
// TODO Here is where the code goes for setting the Job bean's completed property to the current time,
// then updating the database.
// Also set each of the job's OrderDetail items to the same timestamp if they haven't already been set.
for (OrderDetail orderDetail : job.getOrderDetailList()) {
if (orderDetail.getItemCompleted() == null) {
// Only set the current OrderDetail item to completed if it isn't already set as completed.
logger.log(Level.INFO, "Setting the OrderDetail " + orderDetail.getProductId() + " to completion at " + System.currentTimeMillis());
// TODO Somehow set the checkbox as checked.
logger.log(Level.INFO, "Item property is a " + treeTable.getItem(orderDetail.getId()).getItemProperty("Name / Product").getType().getName()); // com.vaadin.ui.CheckBox
CheckBox cbod = (CheckBox)treeTable.getItem(orderDetail.getId()).getItemProperty("Name / Product");
cbod.setValue(true);
}
}
} else {
logger.log(Level.INFO, "Job " + job.getJobId() + " unchecked, clearing timestamp.");
// TODO Code here for setting the Job bean's completed property to null,
// then updating the database.
// Also set each of the job's OrderDetail items to the same timestamp if they haven't already been set.
for (OrderDetail orderDetail : job.getOrderDetailList()) {
if (orderDetail.getItemCompleted() != null) {
// Only set the current OrderDetail item to completed if it isn't already set as completed.
logger.log(Level.INFO, "Clearing the OrderDetail " + orderDetail.getProductId() + "'s completion date.");
// TODO Somehow set the checkbox as checked.
treeTable.getItem(orderDetail.getId()).getItemProperty("Name / Product").setValue(false);
}
}
}
}
And, of course, the error that I mentioned in the original post happens on line 17.
Now, I know this is a lot of code and, despite my efforts to comment it up, it is still difficult to follow, so please don’t hesitate to ask questions about it if you’re confused by why I did one thing or another. And thanks again for the offer to help! I greatly appreciate it!