diff --git a/navalplanner-webapp/src/main/java/org/navalplanner/web/planner/allocation/AllocationRow.java b/navalplanner-webapp/src/main/java/org/navalplanner/web/planner/allocation/AllocationRow.java index dca7dc927..5cb6f1442 100644 --- a/navalplanner-webapp/src/main/java/org/navalplanner/web/planner/allocation/AllocationRow.java +++ b/navalplanner-webapp/src/main/java/org/navalplanner/web/planner/allocation/AllocationRow.java @@ -37,12 +37,18 @@ import org.navalplanner.business.planner.entities.allocationalgorithms.HoursModi import org.navalplanner.business.planner.entities.allocationalgorithms.ResourcesPerDayModification; import org.navalplanner.business.resources.entities.Resource; import org.navalplanner.web.common.Util; +import org.navalplanner.web.planner.allocation.ResourceAllocationController.DerivedAllocationColumn; +import org.zkoss.zk.ui.Component; import org.zkoss.zk.ui.event.EventListener; import org.zkoss.zk.ui.event.Events; import org.zkoss.zul.Constraint; import org.zkoss.zul.Decimalbox; +import org.zkoss.zul.Detail; +import org.zkoss.zul.Grid; import org.zkoss.zul.Intbox; +import org.zkoss.zul.Label; import org.zkoss.zul.SimpleConstraint; +import org.zkoss.zul.SimpleListModel; /** * The information that must be introduced to create a @@ -167,6 +173,8 @@ public abstract class AllocationRow { private final Decimalbox resourcesPerDayInput = new Decimalbox(); + private Grid derivedAllocationsGrid; + private void initializeResourcesPerDayInput() { resourcesPerDayInput.setConstraint(new SimpleConstraint( SimpleConstraint.NO_NEGATIVE)); @@ -349,4 +357,47 @@ public abstract class AllocationRow { resourcesPerDayRowInputChange); } + public void reloadDerivedAllocationsGrid() { + if (hasDerivedAllocations() && !(currentDetail instanceof Detail)) { + replaceOld(currentDetail, createDetail()); + } + reloadDerivedAllocationsData(); + } + + private void reloadDerivedAllocationsData() { + if (derivedAllocationsGrid != null) { + derivedAllocationsGrid.setModel(new SimpleListModel( + getDerivedAllocations())); + } + } + + private void replaceOld(Component oldDetail, Component newDetail) { + Component parent = oldDetail.getParent(); + parent.insertBefore(newDetail, oldDetail); + parent.removeChild(oldDetail); + } + + private Component currentDetail; + + public Component createDetail() { + if (!hasDerivedAllocations()) { + return currentDetail = new Label(); + } + Detail result = new Detail(); + createDerivedAllocationsGrid(); + result.appendChild(derivedAllocationsGrid); + reloadDerivedAllocationsData(); + return currentDetail = result; + } + + private void createDerivedAllocationsGrid() { + if (derivedAllocationsGrid != null) { + return; + } + derivedAllocationsGrid = new Grid(); + DerivedAllocationColumn.appendColumnsTo(derivedAllocationsGrid); + derivedAllocationsGrid.setRowRenderer(DerivedAllocationColumn + .createRenderer()); + } + } diff --git a/navalplanner-webapp/src/main/java/org/navalplanner/web/planner/allocation/FormBinder.java b/navalplanner-webapp/src/main/java/org/navalplanner/web/planner/allocation/FormBinder.java index b2b1e0024..43a374141 100644 --- a/navalplanner-webapp/src/main/java/org/navalplanner/web/planner/allocation/FormBinder.java +++ b/navalplanner-webapp/src/main/java/org/navalplanner/web/planner/allocation/FormBinder.java @@ -369,6 +369,7 @@ class FormBinder { loadValueForAssignedHoursComponent(); loadValueForTaskStartDateBox(); loadValueForEndDate(); + loadDerivedAllocations(); } private void loadHoursValues() { @@ -377,6 +378,12 @@ class FormBinder { } } + private void loadDerivedAllocations() { + for (AllocationRow each : rows) { + each.reloadDerivedAllocationsGrid(); + } + } + public void setApplyButton(Button applyButton) { this.applyButton = applyButton; this.applyButton.setDisabled(true); diff --git a/navalplanner-webapp/src/main/java/org/navalplanner/web/planner/allocation/ResourceAllocationController.java b/navalplanner-webapp/src/main/java/org/navalplanner/web/planner/allocation/ResourceAllocationController.java index e2d23f231..e54b61037 100644 --- a/navalplanner-webapp/src/main/java/org/navalplanner/web/planner/allocation/ResourceAllocationController.java +++ b/navalplanner-webapp/src/main/java/org/navalplanner/web/planner/allocation/ResourceAllocationController.java @@ -34,6 +34,7 @@ import org.joda.time.LocalDate; import org.navalplanner.business.orders.entities.AggregatedHoursGroup; import org.navalplanner.business.planner.entities.AggregateOfResourceAllocations; import org.navalplanner.business.planner.entities.CalculatedValue; +import org.navalplanner.business.planner.entities.DerivedAllocation; import org.navalplanner.business.planner.entities.ResourceAllocation; import org.navalplanner.business.planner.entities.Task; import org.navalplanner.business.resources.entities.ResourceEnum; @@ -49,6 +50,7 @@ import org.navalplanner.web.planner.order.PlanningState; import org.springframework.beans.factory.config.BeanDefinition; import org.springframework.context.annotation.Scope; import org.zkoss.ganttz.timetracker.ICellForDetailItemRenderer; +import org.zkoss.ganttz.timetracker.IConvertibleToColumn; import org.zkoss.ganttz.timetracker.OnColumnsRowRenderer; import org.zkoss.ganttz.util.OnZKDesktopRegistry; import org.zkoss.ganttz.util.script.IScriptsRegister; @@ -60,6 +62,8 @@ import org.zkoss.zk.ui.event.EventListener; import org.zkoss.zk.ui.util.GenericForwardComposer; import org.zkoss.zul.Button; import org.zkoss.zul.Checkbox; +import org.zkoss.zul.Column; +import org.zkoss.zul.Columns; import org.zkoss.zul.Datebox; import org.zkoss.zul.Decimalbox; import org.zkoss.zul.Grid; @@ -445,6 +449,63 @@ public class ResourceAllocationController extends GenericForwardComposer { } } + public enum DerivedAllocationColumn implements IConvertibleToColumn { + NAME("Name") { + @Override + public Component cellFor(DerivedAllocation data) { + return new Label(data.getName()); + } + }, + ALPHA("Alpha") { + @Override + public Component cellFor(DerivedAllocation data) { + return new Label(String.format("%3.2f", data.getAlpha())); + } + }, + HOURS("Total Hours") { + @Override + public Component cellFor(DerivedAllocation data) { + return new Label(data.getHours() + ""); + } + }; + + private final String name; + + private DerivedAllocationColumn(String name) { + this.name = name; + } + + @Override + public org.zkoss.zul.api.Column toColumn() { + return new Column(_(name)); + } + + public static void appendColumnsTo(Grid grid) { + Columns columns = new Columns(); + grid.appendChild(columns); + for (DerivedAllocationColumn each : values()) { + columns.appendChild(each.toColumn()); + } + } + + public static RowRenderer createRenderer() { + return OnColumnsRowRenderer.create(cellRenderer, Arrays + .asList(DerivedAllocationColumn.values())); + } + + private static final ICellForDetailItemRenderer cellRenderer= new ICellForDetailItemRenderer() { + + @Override + public Component cellFor( + DerivedAllocationColumn column, + DerivedAllocation data) { + return column.cellFor(data); + } + }; + + abstract Component cellFor(DerivedAllocation data); + } + public List getCalculationTypes() { return Arrays.asList(CalculationTypeRadio.values()); } @@ -534,7 +595,7 @@ public class ResourceAllocationController extends GenericForwardComposer { private void renderResourceAllocation(Row row, final AllocationRow data) throws Exception { row.setValue(data); - // Label fields are fixed, can only be viewed + append(row, data.createDetail()); append(row, new Label(data.getName())); append(row, data.getHoursInput()); append(row, data.getResourcesPerDayInput()); diff --git a/navalplanner-webapp/src/main/webapp/planner/order.zul b/navalplanner-webapp/src/main/webapp/planner/order.zul index d7981e711..18a7f6aaf 100644 --- a/navalplanner-webapp/src/main/webapp/planner/order.zul +++ b/navalplanner-webapp/src/main/webapp/planner/order.zul @@ -160,6 +160,7 @@ rowRenderer="@{allocationController.resourceAllocationRenderer}" style="margin-bottom: 5px" fixedLayout="true"> +