package org.dodgybits.shuffle.web.client;
import java.util.ArrayList;
import java.util.Date;
import org.dodgybits.shuffle.web.client.command.GetTasksCommand;
import org.dodgybits.shuffle.web.client.command.SaveTaskCommand;
import org.dodgybits.shuffle.web.client.formatter.ActionDateFormatter;
import org.dodgybits.shuffle.web.client.model.TaskValue;
import org.dodgybits.shuffle.web.client.service.ErrorHandlingAsyncCallback;
import com.google.gwt.core.client.GWT;
import com.google.gwt.event.dom.client.ClickEvent;
import com.google.gwt.event.dom.client.ClickHandler;
import com.google.gwt.resources.client.CssResource;
import com.google.gwt.uibinder.client.UiBinder;
import com.google.gwt.uibinder.client.UiField;
import com.google.gwt.user.client.DOM;
import com.google.gwt.user.client.Element;
import com.google.gwt.user.client.ui.FlexTable;
import com.google.gwt.user.client.ui.FlowPanel;
import com.google.gwt.user.client.ui.ResizeComposite;
import com.google.gwt.user.client.ui.Widget;
import com.google.gwt.user.client.ui.HTMLTable.Cell;
import com.google.inject.Inject;
/**
* A composite that displays a list of actions.
*/
public class TaskList extends ResizeComposite implements ClickHandler {
interface Binder extends UiBinder<Widget, TaskList> {
}
interface SelectionStyle extends CssResource {
String selectedRow();
}
private static final Binder sBinder = GWT.create(Binder.class);
private ActionDateFormatter mFormatter;
private GetTasksCommand.Factory mGetTasksFactory;
private SaveTaskCommand.Factory mSaveTaskFactory;
private ArrayList<TaskValue> taskValues;
@UiField
FlowPanel header;
@UiField
FlowPanel footer;
@UiField
FlexTable table;
@UiField
SelectionStyle selectionStyle;
@Inject
public TaskList(GetTasksCommand.Factory factory,
SaveTaskCommand.Factory saveTaskFactory,
ActionDateFormatter formatter) {
mGetTasksFactory = factory;
mSaveTaskFactory = saveTaskFactory;
mFormatter = formatter;
initWidget(sBinder.createAndBindUi(this));
initTable();
}
private void initTable() {
// Initialize the table.
table.getColumnFormatter().setWidth(1, "10em");
table.addClickHandler(this);
fetchActions();
}
private void fetchActions() {
GetTasksCommand command = mGetTasksFactory
.create(new ErrorHandlingAsyncCallback<ArrayList<TaskValue>>() {
@Override
public void onSuccess(ArrayList<TaskValue> result) {
taskValues = result;
displayActions();
}
});
command.execute();
}
private void saveAction(final int taskValueIndex) {
TaskValue task = taskValues.get(taskValueIndex);
SaveTaskCommand command = mSaveTaskFactory
.create(task,
new ErrorHandlingAsyncCallback<TaskValue>() {
@Override
public void onSuccess(TaskValue result) {
taskValues.set(taskValueIndex, result);
}
});
command.execute();
}
private void displayActions() {
int numActions = taskValues.size();
for (int i = 0; i < numActions; i++) {
TaskValue taskValue = taskValues.get(i);
displayAction(taskValue, i);
}
}
@Override
public void onClick(ClickEvent event) {
Cell clickedCell = table.getCellForEvent(event);
int rowIndex = clickedCell.getRowIndex();
saveAction(rowIndex);
}
private void displayAction(TaskValue taskValue, int row) {
String description = "<div class='actionTitle'>"
+ escapeHtml(taskValue.getTitle())
+ "<span class='actionDetails'> - "
+ escapeHtml(taskValue.getDetails()) + "</span></div>";
table.setHTML(row, 0, description);
table.setText(row, 1, mFormatter.getShortDueDate(taskValue));
table.getCellFormatter().setStyleName(
row,
1,
isInPast(taskValue.getDueDate()) ? "actionDueInPass"
: "actionDueInFuture");
}
private static String escapeHtml(String maybeHtml) {
final Element div = DOM.createDiv();
DOM.setInnerText(div, maybeHtml);
return DOM.getInnerHTML(div);
}
private static boolean isInPast(Date date) {
return date != null && date.getTime() < System.currentTimeMillis();
}
}