mirror of
https://github.com/eclipse-sailing-analytics/sailing-analytics.git
synced 2026-10-21 19:50:01 +00:00
3-table course designer
This commit is contained in:
1 parent
7fa3e066b6
commit
70ae0e9543
15 files changed
+577
-466
No files matched your search
+41
@@ -0,0 +1,41 @@
|
||||
package com.sap.sailing.gwt.ui.adminconsole;
|
||||
|
||||
import com.google.gwt.user.cellview.client.TextColumn;
|
||||
import com.google.gwt.view.client.SelectionModel;
|
||||
import com.sap.sailing.gwt.ui.client.ErrorReporter;
|
||||
import com.sap.sailing.gwt.ui.client.SailingServiceAsync;
|
||||
import com.sap.sailing.gwt.ui.client.StringMessages;
|
||||
import com.sap.sailing.gwt.ui.shared.ControlPointDTO;
|
||||
import com.sap.sailing.gwt.ui.shared.GateDTO;
|
||||
import com.sap.sailing.gwt.ui.shared.MarkDTO;
|
||||
|
||||
public class ControlPointTableWrapper<S extends SelectionModel<ControlPointDTO>> extends TableWrapper<ControlPointDTO, S> {
|
||||
public ControlPointTableWrapper(S selectionModel, SailingServiceAsync sailingService, final StringMessages stringMessages,
|
||||
ErrorReporter errorReporter) {
|
||||
super(sailingService, stringMessages, errorReporter, selectionModel);
|
||||
|
||||
mainPanel.add(table);
|
||||
|
||||
TextColumn<ControlPointDTO> nameColumn = new TextColumn<ControlPointDTO>() {
|
||||
@Override
|
||||
public String getValue(ControlPointDTO d) {
|
||||
return d.getName();
|
||||
}
|
||||
};
|
||||
table.addColumn(nameColumn, stringMessages.name());
|
||||
|
||||
TextColumn<ControlPointDTO> typeColumn = new TextColumn<ControlPointDTO>() {
|
||||
@Override
|
||||
public String getValue(ControlPointDTO d) {
|
||||
if (d instanceof GateDTO) {
|
||||
return "2x " + stringMessages.mark();
|
||||
} else if (d instanceof MarkDTO) {
|
||||
return stringMessages.mark();
|
||||
} else {
|
||||
return stringMessages.unknown();
|
||||
}
|
||||
}
|
||||
};
|
||||
table.addColumn(typeColumn, stringMessages.type());
|
||||
}
|
||||
}
|
||||
+178
-415
@@ -1,34 +1,28 @@
|
||||
package com.sap.sailing.gwt.ui.adminconsole;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashSet;
|
||||
import java.util.Iterator;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
import java.util.Map;
|
||||
|
||||
import com.google.gwt.cell.client.FieldUpdater;
|
||||
import com.google.gwt.core.client.GWT;
|
||||
import com.google.gwt.dom.client.Style.FontWeight;
|
||||
import com.google.gwt.core.shared.GWT;
|
||||
import com.google.gwt.event.dom.client.ClickEvent;
|
||||
import com.google.gwt.event.dom.client.ClickHandler;
|
||||
import com.google.gwt.user.cellview.client.CellTable;
|
||||
import com.google.gwt.user.cellview.client.TextColumn;
|
||||
import com.google.gwt.user.client.ui.Button;
|
||||
import com.google.gwt.user.client.ui.CaptionPanel;
|
||||
import com.google.gwt.user.client.ui.Grid;
|
||||
import com.google.gwt.user.client.ui.HasVerticalAlignment;
|
||||
import com.google.gwt.user.client.ui.HorizontalPanel;
|
||||
import com.google.gwt.user.client.ui.IsWidget;
|
||||
import com.google.gwt.user.client.ui.Label;
|
||||
import com.google.gwt.user.client.ui.ListBox;
|
||||
import com.google.gwt.user.client.ui.VerticalPanel;
|
||||
import com.google.gwt.user.client.ui.Widget;
|
||||
import com.google.gwt.view.client.ListDataProvider;
|
||||
import com.google.gwt.view.client.MultiSelectionModel;
|
||||
import com.google.gwt.view.client.SelectionChangeEvent;
|
||||
import com.google.gwt.view.client.SelectionChangeEvent.Handler;
|
||||
import com.google.gwt.view.client.SetSelectionModel;
|
||||
import com.google.gwt.view.client.SingleSelectionModel;
|
||||
import com.sap.sailing.domain.common.PassingInstruction;
|
||||
import com.sap.sailing.domain.common.impl.Util.Pair;
|
||||
import com.sap.sailing.domain.common.impl.Util;
|
||||
import com.sap.sailing.gwt.ui.client.ErrorReporter;
|
||||
import com.sap.sailing.gwt.ui.client.SailingServiceAsync;
|
||||
import com.sap.sailing.gwt.ui.client.StringMessages;
|
||||
@@ -40,180 +34,25 @@ import com.sap.sailing.gwt.ui.shared.WaypointDTO;
|
||||
import com.sap.sse.gwt.client.dialog.DataEntryDialog;
|
||||
|
||||
public abstract class CourseManagementWidget implements IsWidget {
|
||||
/**
|
||||
* Represents one mark assignment for a control point. Gates have multiple such records, one for each of their marks.
|
||||
*
|
||||
* @author Axel Uhl (D043530)
|
||||
*/
|
||||
public static class ControlPointAndOldAndNewMark {
|
||||
protected final ControlPointDTO controlPoint;
|
||||
protected final MarkDTO oldMark;
|
||||
protected MarkDTO newMark;
|
||||
protected PassingInstruction passingInstructions;
|
||||
public ControlPointAndOldAndNewMark(ControlPointDTO controlPoint, PassingInstruction passingInstructions, MarkDTO oldMark) {
|
||||
super();
|
||||
this.controlPoint = controlPoint;
|
||||
this.passingInstructions = passingInstructions;
|
||||
this.oldMark = oldMark;
|
||||
this.newMark = oldMark;
|
||||
}
|
||||
public PassingInstruction getPassingInstructions() {
|
||||
return passingInstructions;
|
||||
}
|
||||
public MarkDTO getNewMark() {
|
||||
return newMark;
|
||||
}
|
||||
public void setNewMark(MarkDTO newMark) {
|
||||
this.newMark = newMark;
|
||||
}
|
||||
public ControlPointDTO getControlPoint() {
|
||||
return controlPoint;
|
||||
}
|
||||
public MarkDTO getOldMark() {
|
||||
return oldMark;
|
||||
}
|
||||
}
|
||||
protected final MarkTableWrapper<MultiSelectionModel<MarkDTO>> marks;
|
||||
protected final ControlPointTableWrapper<MultiSelectionModel<ControlPointDTO>> multiMarkControlPoints;
|
||||
protected final WaypointTableWrapper<SingleSelectionModel<WaypointDTO>> waypoints;
|
||||
|
||||
private class ControlPointCreationDialog extends DataEntryDialog<Pair<ControlPointDTO, PassingInstruction>> {
|
||||
private final MarkTableWrapper<MultiSelectionModel<MarkDTO>> marksTable;
|
||||
private final MultiSelectionModel<MarkDTO> selectionModel;
|
||||
private final ListBox passingInstructions;
|
||||
private final StringMessages stringMessages;
|
||||
|
||||
public ControlPointCreationDialog(final StringMessages stringMessages, AdminConsoleTableResources tableRes,
|
||||
List<MarkDTO> marks, DialogCallback<Pair<ControlPointDTO, PassingInstruction>> callback) {
|
||||
super(stringMessages.controlPoint(), stringMessages.selectOneMarkOrTwoMarksForGate(),
|
||||
stringMessages.ok(), stringMessages.cancel(), new DataEntryDialog.Validator<Pair<ControlPointDTO, PassingInstruction>>() {
|
||||
@Override
|
||||
public String getErrorMessage(Pair<ControlPointDTO, PassingInstruction> valueToValidate) {
|
||||
if (valueToValidate.getA() == null) {
|
||||
return stringMessages.selectOneMarkOrTwoMarksForGate();
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
}, /* animationEnabled */ false, callback);
|
||||
|
||||
this.stringMessages = stringMessages;
|
||||
|
||||
selectionModel = new MultiSelectionModel<MarkDTO>();
|
||||
selectionModel.addSelectionChangeHandler(new Handler() {
|
||||
@Override
|
||||
public void onSelectionChange(SelectionChangeEvent event) {
|
||||
updatePassingInstructions();
|
||||
validate();
|
||||
}
|
||||
});
|
||||
marksTable = new MarkTableWrapper<MultiSelectionModel<MarkDTO>>(
|
||||
selectionModel, CourseManagementWidget.this.sailingService, stringMessages, errorReporter);
|
||||
marksTable.getDataProvider().getList().addAll(marks);
|
||||
|
||||
passingInstructions = createListBox(false);
|
||||
updatePassingInstructions();
|
||||
}
|
||||
|
||||
private void updatePassingInstructions() {
|
||||
passingInstructions.clear();
|
||||
|
||||
int numSelectedMarks = selectionModel.getSelectedSet().size();
|
||||
int i = 0;
|
||||
passingInstructions.insertItem(PassingInstruction.None.name(), i++);
|
||||
for (PassingInstruction pi : PassingInstruction.relevantValues()) {
|
||||
for (int numApplicableMarks : pi.applicability) {
|
||||
if (numApplicableMarks == numSelectedMarks) {
|
||||
passingInstructions.insertItem(pi.name(), i++);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Pair<ControlPointDTO, PassingInstruction> getResult() {
|
||||
ControlPointDTO controlPoint = null;
|
||||
Set<MarkDTO> selection = selectionModel.getSelectedSet();
|
||||
if (selection.size() == 1) {
|
||||
controlPoint = selectionModel.getSelectedSet().iterator().next();
|
||||
} else if (selection.size() == 2) {
|
||||
Iterator<MarkDTO> i = selectionModel.getSelectedSet().iterator();
|
||||
MarkDTO first = i.next();
|
||||
MarkDTO second = i.next();
|
||||
MarkDTO left;
|
||||
MarkDTO right;
|
||||
String gateName;
|
||||
if (first.getName().matches("^.*"+REGEX_FOR_LEFT+".*$")) {
|
||||
left = first;
|
||||
right = second;
|
||||
} else {
|
||||
left = second;
|
||||
right = first;
|
||||
}
|
||||
gateName = left.getName().replaceFirst(REGEX_FOR_LEFT, "");
|
||||
controlPoint = new GateDTO(/* generate UUID on the server */ null, gateName, left, right);
|
||||
}
|
||||
|
||||
PassingInstruction passingInstruction =
|
||||
passingInstructions.getSelectedIndex() == -1 ? PassingInstruction.None :
|
||||
PassingInstruction.valueOf(passingInstructions.getValue(passingInstructions.getSelectedIndex()));
|
||||
|
||||
return new Pair<ControlPointDTO, PassingInstruction>(controlPoint, passingInstruction);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Widget getAdditionalWidget() {
|
||||
Grid grid = new Grid(2,1);
|
||||
grid.setWidget(0, 0, marksTable);
|
||||
|
||||
HorizontalPanel passingInstructionsRow = new HorizontalPanel();
|
||||
grid.setWidget(1, 0, passingInstructionsRow);
|
||||
passingInstructionsRow.add(new Label(stringMessages.passingInstructions() + ":"));
|
||||
passingInstructionsRow.add(passingInstructions);
|
||||
|
||||
return grid;
|
||||
}
|
||||
}
|
||||
protected final Grid mainPanel;
|
||||
|
||||
protected static final String REGEX_FOR_LEFT = "( \\()?(([lL][eE][fF][tT])|(1))\\)?";
|
||||
|
||||
/**
|
||||
* A table that lists the marks for which events have been received for the race selected. Note that this list may
|
||||
* be longer than the list of marks actually used by the control points backing the course's waypoints because of
|
||||
* the possibility of spare marks.
|
||||
*/
|
||||
protected final SingleSelectionModel<MarkDTO> markSelectionModel;
|
||||
|
||||
/**
|
||||
* A table that lists the product of Waypoint x ControlPoint x Mark plus a hint as to the number of mark passings.
|
||||
* The (multi-)selection on this table can be used as either a selection of waypoints or a selection of control points
|
||||
* or a selection of marks.
|
||||
*/
|
||||
protected final CellTable<ControlPointAndOldAndNewMark> controlPointsTable;
|
||||
protected final MultiSelectionModel<ControlPointAndOldAndNewMark> controlPointsSelectionModel;
|
||||
protected final ListDataProvider<ControlPointAndOldAndNewMark> controlPointDataProvider;
|
||||
|
||||
/**
|
||||
* When for a control point's mark a replacement mark is defined (see {@link #updateNewMark(Set, MarkDTO)}),
|
||||
* the control point needs to be replaced before {@link #saveCourse(SailingServiceAsync, StringMessages) saving}.
|
||||
* Those control points are added to this set. When the mark is reset to the original mark for all the control
|
||||
* point's marks, the control point is removed from this set again. {@link #saveCourse(SailingServiceAsync, StringMessages)}
|
||||
* then is responsible for creating replacement {@link ControlPointDTO}s before sending the new control point list to the
|
||||
* server.
|
||||
*/
|
||||
protected final Set<ControlPointDTO> controlPointsNeedingReplacement;
|
||||
|
||||
protected final HorizontalPanel courseActionsPanel;
|
||||
|
||||
protected final VerticalPanel mainPanel;
|
||||
|
||||
protected MarkTableWrapper<SingleSelectionModel<MarkDTO>> marksTable;
|
||||
|
||||
protected final Handler markSelectionChangeHandler;
|
||||
protected final Button insertWaypointBefore;
|
||||
protected final Button insertWaypointAfter;
|
||||
protected final Button saveButton;
|
||||
protected boolean ignoreWaypointAndOldAndNewMarkSelectionChange;
|
||||
protected final SailingServiceAsync sailingService;
|
||||
protected final ErrorReporter errorReporter;
|
||||
protected final StringMessages stringMessages;
|
||||
|
||||
protected final HorizontalPanel waypointsBtnsPanel;
|
||||
protected final HorizontalPanel controlPointsBtnsPanel;
|
||||
protected final HorizontalPanel marksBtnsPanel;
|
||||
protected final HorizontalPanel buttonsPanel;
|
||||
|
||||
protected final Button insertWaypointBefore;
|
||||
protected final Button insertWaypointAfter;
|
||||
|
||||
protected final AdminConsoleTableResources tableRes = GWT.create(AdminConsoleTableResources.class);
|
||||
|
||||
@Override
|
||||
public Widget asWidget() {
|
||||
@@ -224,119 +63,101 @@ public abstract class CourseManagementWidget implements IsWidget {
|
||||
final StringMessages stringMessages) {
|
||||
this.sailingService = sailingService;
|
||||
this.errorReporter = errorReporter;
|
||||
mainPanel = new VerticalPanel();
|
||||
this.stringMessages = stringMessages;
|
||||
|
||||
controlPointsNeedingReplacement = new HashSet<ControlPointDTO>();
|
||||
Grid grid = new Grid(2, 2);
|
||||
grid.setCellPadding(5);
|
||||
|
||||
mainPanel.add(grid);
|
||||
mainPanel = new Grid(3, 3);
|
||||
mainPanel.setCellPadding(5);
|
||||
mainPanel.getRowFormatter().setVerticalAlign(0, HasVerticalAlignment.ALIGN_TOP);
|
||||
|
||||
Label currentRaceCourseLabel = new Label("Current race course");
|
||||
currentRaceCourseLabel.getElement().getStyle().setFontWeight(FontWeight.BOLD);
|
||||
grid.setWidget(0, 0, currentRaceCourseLabel);
|
||||
Label availableMarksLabel = new Label("Available marks");
|
||||
availableMarksLabel.getElement().getStyle().setFontWeight(FontWeight.BOLD);
|
||||
grid.setWidget(0, 1, availableMarksLabel);
|
||||
grid.getRowFormatter().setVerticalAlign(1, HasVerticalAlignment.ALIGN_TOP);
|
||||
waypoints = new WaypointTableWrapper<SingleSelectionModel<WaypointDTO>>(
|
||||
new SingleSelectionModel<WaypointDTO>(), sailingService, stringMessages, errorReporter);
|
||||
multiMarkControlPoints = new ControlPointTableWrapper<MultiSelectionModel<ControlPointDTO>>(
|
||||
new MultiSelectionModel<ControlPointDTO>(), sailingService, stringMessages, errorReporter);
|
||||
marks = new MarkTableWrapper<MultiSelectionModel<MarkDTO>>(
|
||||
new MultiSelectionModel<MarkDTO>(), sailingService, stringMessages, errorReporter);
|
||||
|
||||
final AdminConsoleTableResources tableRes = GWT.create(AdminConsoleTableResources.class);
|
||||
controlPointsTable = new CellTable<ControlPointAndOldAndNewMark>(/* pageSize */10000, tableRes);
|
||||
grid.setWidget(1, 0, controlPointsTable);
|
||||
controlPointsSelectionModel = new MultiSelectionModel<ControlPointAndOldAndNewMark>();
|
||||
controlPointsTable.setSelectionModel(controlPointsSelectionModel);
|
||||
controlPointsSelectionModel.addSelectionChangeHandler(new Handler() {
|
||||
@Override
|
||||
public void onSelectionChange(SelectionChangeEvent event) {
|
||||
handleControlPointSelectionChange();
|
||||
}
|
||||
});
|
||||
TextColumn<ControlPointAndOldAndNewMark> nameColumn = new TextColumn<ControlPointAndOldAndNewMark>() {
|
||||
@Override
|
||||
public String getValue(ControlPointAndOldAndNewMark cpaoanm) {
|
||||
return cpaoanm.getControlPoint().getName();
|
||||
}
|
||||
};
|
||||
controlPointsTable.addColumn(nameColumn, stringMessages.controlPoint());
|
||||
TextColumn<ControlPointAndOldAndNewMark> passingInstructionsColumn = new TextColumn<ControlPointAndOldAndNewMark>() {
|
||||
@Override
|
||||
public String getValue(ControlPointAndOldAndNewMark cpaoanm) {
|
||||
String result = "";
|
||||
if(cpaoanm.getPassingInstructions() != null) {
|
||||
result = cpaoanm.getPassingInstructions().name();
|
||||
}
|
||||
return result;
|
||||
}
|
||||
};
|
||||
controlPointsTable.addColumn(passingInstructionsColumn, "Passing instructions");
|
||||
TextColumn<ControlPointAndOldAndNewMark> oldMarkColumn = new TextColumn<ControlPointAndOldAndNewMark>() {
|
||||
@Override
|
||||
public String getValue(ControlPointAndOldAndNewMark cpaoanm) {
|
||||
return "" + cpaoanm.getOldMark().getName();
|
||||
}
|
||||
};
|
||||
controlPointsTable.addColumn(oldMarkColumn, stringMessages.mark());
|
||||
TextColumn<ControlPointAndOldAndNewMark> newMarkColumn = new TextColumn<ControlPointAndOldAndNewMark>(){
|
||||
|
||||
@Override
|
||||
public String getValue(ControlPointAndOldAndNewMark cpaoanm) {
|
||||
return "" + cpaoanm.getNewMark().getName();
|
||||
}
|
||||
|
||||
};
|
||||
controlPointsTable.addColumn(newMarkColumn, stringMessages.newMark());
|
||||
|
||||
ImagesBarColumn<ControlPointAndOldAndNewMark, CourseManagementWidgetWaypointsImagesBarCell> actionColumn =
|
||||
new ImagesBarColumn<ControlPointAndOldAndNewMark, CourseManagementWidgetWaypointsImagesBarCell>(
|
||||
CaptionPanel waypointsPanel = new CaptionPanel(stringMessages.waypoints());
|
||||
CaptionPanel controlPointsPanel = new CaptionPanel(stringMessages.twoMarkControlPoint());
|
||||
CaptionPanel marksPanel = new CaptionPanel(stringMessages.mark());
|
||||
waypointsPanel.add(waypoints);
|
||||
controlPointsPanel.add(multiMarkControlPoints);
|
||||
marksPanel.add(marks);
|
||||
mainPanel.setWidget(0, 0, waypointsPanel);
|
||||
mainPanel.setWidget(0, 1, controlPointsPanel);
|
||||
mainPanel.setWidget(0, 2, marksPanel);
|
||||
|
||||
waypointsBtnsPanel = new HorizontalPanel();
|
||||
controlPointsBtnsPanel = new HorizontalPanel();
|
||||
marksBtnsPanel = new HorizontalPanel();
|
||||
mainPanel.setWidget(1, 0, waypointsBtnsPanel);
|
||||
mainPanel.setWidget(1, 1, controlPointsBtnsPanel);
|
||||
mainPanel.setWidget(1, 2, marksBtnsPanel);
|
||||
|
||||
ImagesBarColumn<WaypointDTO, CourseManagementWidgetWaypointsImagesBarCell> waypointsActionColumn =
|
||||
new ImagesBarColumn<WaypointDTO, CourseManagementWidgetWaypointsImagesBarCell>(
|
||||
new CourseManagementWidgetWaypointsImagesBarCell(stringMessages));
|
||||
actionColumn.setFieldUpdater(new FieldUpdater<ControlPointAndOldAndNewMark, String>() {
|
||||
waypointsActionColumn.setFieldUpdater(new FieldUpdater<WaypointDTO, String>() {
|
||||
@Override
|
||||
public void update(int index, ControlPointAndOldAndNewMark controlPoint, String value) {
|
||||
public void update(int index, WaypointDTO waypoint, String value) {
|
||||
if (CourseManagementWidgetWaypointsImagesBarCell.ACTION_DELETE.equals(value)) {
|
||||
removeSelectedWaypoints(sailingService);
|
||||
removeWaypoint(waypoint);
|
||||
}
|
||||
}
|
||||
});
|
||||
controlPointsTable.addColumn(actionColumn, stringMessages.actions());
|
||||
controlPointDataProvider = new ListDataProvider<ControlPointAndOldAndNewMark>();
|
||||
controlPointDataProvider.addDataDisplay(controlPointsTable);
|
||||
|
||||
// race course marks table
|
||||
markSelectionModel = new SingleSelectionModel<MarkDTO>();
|
||||
marksTable = new MarkTableWrapper<SingleSelectionModel<MarkDTO>>(markSelectionModel, sailingService, stringMessages, errorReporter);
|
||||
markSelectionChangeHandler = new Handler() {
|
||||
waypoints.getTable().addColumn(waypointsActionColumn);
|
||||
|
||||
waypoints.getSelectionModel().addSelectionChangeHandler(new Handler() {
|
||||
@Override
|
||||
public void onSelectionChange(SelectionChangeEvent event) {
|
||||
if (!ignoreWaypointAndOldAndNewMarkSelectionChange) {
|
||||
updateNewMark(controlPointsSelectionModel.getSelectedSet(), markSelectionModel.getSelectedObject());
|
||||
WaypointDTO waypoint = waypoints.getSelectionModel().getSelectedObject();
|
||||
if (waypoint != null) {
|
||||
selectControlPoints(waypoint);
|
||||
selectMarks(waypoint.marks);
|
||||
}
|
||||
updateWaypointButtons();
|
||||
}
|
||||
});
|
||||
|
||||
multiMarkControlPoints.getSelectionModel().addSelectionChangeHandler(new Handler() {
|
||||
@Override
|
||||
public void onSelectionChange(SelectionChangeEvent event) {
|
||||
if (multiMarkControlPoints.getSelectionModel().getSelectedSet().size() > 0) {
|
||||
ControlPointDTO first = multiMarkControlPoints.getSelectionModel().getSelectedSet().iterator().next();
|
||||
selectMarks(first.getMarks());
|
||||
}
|
||||
}
|
||||
};
|
||||
markSelectionModel.addSelectionChangeHandler(markSelectionChangeHandler);
|
||||
grid.setWidget(1, 1, marksTable);
|
||||
|
||||
courseActionsPanel = new HorizontalPanel();
|
||||
courseActionsPanel.setSpacing(10);
|
||||
});
|
||||
|
||||
insertWaypointBefore = new Button(stringMessages.insertWaypointBeforeSelected());
|
||||
insertWaypointBefore.addClickHandler(new ClickHandler() {
|
||||
@Override
|
||||
public void onClick(ClickEvent event) {
|
||||
insertWaypoint(sailingService, stringMessages, tableRes, /* before */ true);
|
||||
insertWaypoint(/* before */ true);
|
||||
}
|
||||
|
||||
});
|
||||
insertWaypointBefore.setEnabled(false);
|
||||
courseActionsPanel.add(insertWaypointBefore);
|
||||
waypointsBtnsPanel.add(insertWaypointBefore);
|
||||
insertWaypointAfter = new Button(stringMessages.insertWaypointAfterSelected());
|
||||
insertWaypointAfter.addClickHandler(new ClickHandler() {
|
||||
@Override
|
||||
public void onClick(ClickEvent event) {
|
||||
insertWaypoint(sailingService, stringMessages, tableRes, /* before */ false);
|
||||
insertWaypoint(/* before */ false);
|
||||
}
|
||||
|
||||
});
|
||||
insertWaypointAfter.setEnabled(false);
|
||||
courseActionsPanel.add(insertWaypointAfter);
|
||||
waypointsBtnsPanel.add(insertWaypointAfter);
|
||||
|
||||
final Button addControlPoint = new Button(stringMessages.addGate());
|
||||
addControlPoint.addClickHandler(new ClickHandler() {
|
||||
@Override
|
||||
public void onClick(ClickEvent event) {
|
||||
addMultiMarkControlPoint();
|
||||
}
|
||||
});
|
||||
controlPointsBtnsPanel.add(addControlPoint);
|
||||
|
||||
buttonsPanel = new HorizontalPanel();
|
||||
mainPanel.setWidget(2, 2, buttonsPanel);
|
||||
Button refreshBtn = new Button(stringMessages.refresh());
|
||||
refreshBtn.addClickHandler(new ClickHandler() {
|
||||
@Override
|
||||
@@ -344,178 +165,120 @@ public abstract class CourseManagementWidget implements IsWidget {
|
||||
refresh();
|
||||
}
|
||||
});
|
||||
courseActionsPanel.add(refreshBtn);
|
||||
saveButton = new Button(stringMessages.save());
|
||||
saveButton.addClickHandler(new ClickHandler() {
|
||||
buttonsPanel.add(refreshBtn);
|
||||
Button saveBtn = new Button(stringMessages.save());
|
||||
saveBtn.addClickHandler(new ClickHandler() {
|
||||
@Override
|
||||
public void onClick(ClickEvent event) {
|
||||
Set<ControlPointDTO> oldControlPointsFromTableAlreadyHandled = new HashSet<ControlPointDTO>();
|
||||
List<Pair<ControlPointDTO, PassingInstruction>> controlPoints = new ArrayList<Pair<ControlPointDTO, PassingInstruction>>();
|
||||
for (ControlPointAndOldAndNewMark cpaoanb : controlPointDataProvider.getList()) {
|
||||
if (!oldControlPointsFromTableAlreadyHandled.contains(cpaoanb.getControlPoint())) {
|
||||
oldControlPointsFromTableAlreadyHandled.add(cpaoanb.getControlPoint());
|
||||
ControlPointDTO controlPointToAdd;
|
||||
if (controlPointsNeedingReplacement.contains(cpaoanb.getControlPoint())) {
|
||||
if (cpaoanb.getControlPoint() instanceof GateDTO) {
|
||||
controlPointToAdd = createGate((GateDTO) cpaoanb.getControlPoint());
|
||||
} else {
|
||||
controlPointToAdd = cpaoanb.getNewMark();
|
||||
}
|
||||
} else {
|
||||
controlPointToAdd = cpaoanb.getControlPoint();
|
||||
}
|
||||
controlPoints.add(new Pair<ControlPointDTO, PassingInstruction>(controlPointToAdd, cpaoanb.passingInstructions));
|
||||
}
|
||||
}
|
||||
saveCourse(controlPoints);
|
||||
save();
|
||||
}
|
||||
});␍ courseActionsPanel.add(saveButton);
|
||||
// courseActionsPanel.setVisible(false);
|
||||
|
||||
mainPanel.add(courseActionsPanel);
|
||||
});
|
||||
buttonsPanel.add(saveBtn);
|
||||
}
|
||||
|
||||
private void handleControlPointSelectionChange() {
|
||||
ignoreWaypointAndOldAndNewMarkSelectionChange = true;
|
||||
try {
|
||||
markSelectionModel.setSelected(markSelectionModel.getSelectedObject(), false);
|
||||
final int selectionSize = controlPointsSelectionModel.getSelectedSet().size();
|
||||
insertWaypointAfter.setEnabled(selectionSize==1);
|
||||
insertWaypointBefore.setEnabled(selectionSize==1 || controlPointDataProvider.getList().isEmpty());
|
||||
if (selectionSize == 1) {
|
||||
MarkDTO newMark = controlPointsSelectionModel.getSelectedSet().iterator().next().getNewMark();
|
||||
if (newMark != null) {
|
||||
for (MarkDTO markDTO : marksTable.getDataProvider().getList()) {
|
||||
if (markDTO.getName().equals(newMark.getName())) {
|
||||
markSelectionModel.setSelected(markDTO, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
} finally {
|
||||
ignoreWaypointAndOldAndNewMarkSelectionChange = false;
|
||||
|
||||
private void removeWaypoint(WaypointDTO waypoint) {
|
||||
waypoints.getDataProvider().getList().remove(waypoint);
|
||||
}
|
||||
|
||||
private void selectControlPoints(WaypointDTO waypoint) {
|
||||
for (ControlPointDTO controlPoint : multiMarkControlPoints.getDataProvider().getList()) {
|
||||
multiMarkControlPoints.getSelectionModel().setSelected(
|
||||
controlPoint, waypoint.controlPoint == controlPoint);
|
||||
}
|
||||
}
|
||||
|
||||
private void selectMarks(Iterable<MarkDTO> newMarks) {
|
||||
marks.getSelectionModel().clear();
|
||||
for (MarkDTO toSelect : newMarks) {
|
||||
marks.getSelectionModel().setSelected(toSelect, true);
|
||||
}
|
||||
}
|
||||
|
||||
protected abstract void saveCourse(List<Pair<ControlPointDTO, PassingInstruction>> controlPoints);
|
||||
|
||||
/**
|
||||
* When a gate needs replacement, its entries in {@link #controlPointDataProvider} are looked up, and a new
|
||||
* {@link GateDTO} is created having the same name as the old gate, but using the new marks as the gate's marks.
|
||||
*/
|
||||
protected ControlPointDTO createGate(GateDTO oldGate) {
|
||||
MarkDTO newLeft = null;
|
||||
MarkDTO newRight = null;
|
||||
for (ControlPointAndOldAndNewMark cpaoanb : controlPointDataProvider.getList()) {
|
||||
if (cpaoanb.getControlPoint() == oldGate) {
|
||||
MarkDTO newMark = cpaoanb.getNewMark();
|
||||
if (newRight != null || newMark.getName().matches("^.*"+REGEX_FOR_LEFT+".*$")) {
|
||||
newLeft = newMark;
|
||||
} else {
|
||||
newRight = newMark;
|
||||
}
|
||||
}
|
||||
protected abstract void save();
|
||||
|
||||
private <T> T getFirstSelected(SetSelectionModel<T> selectionModel) {
|
||||
if (selectionModel.getSelectedSet().isEmpty()) {
|
||||
return null;
|
||||
}
|
||||
assert newLeft != null && newRight != null;
|
||||
// if old gate had null ID, the new gate will have a null ID too, causing the server to generate one
|
||||
return new GateDTO(oldGate.getIdAsString(), oldGate.getName(), newLeft, newRight);
|
||||
return selectionModel.getSelectedSet().iterator().next();
|
||||
}
|
||||
|
||||
private void updateNewMark(Set<ControlPointAndOldAndNewMark> selectedWaypointsAndOldAndNewMarks, MarkDTO selectedNewMark) {
|
||||
if (selectedWaypointsAndOldAndNewMarks != null) {
|
||||
for (ControlPointAndOldAndNewMark w : selectedWaypointsAndOldAndNewMarks) {
|
||||
if (selectedNewMark == null) {
|
||||
w.setNewMark(w.getOldMark());
|
||||
} else {
|
||||
w.setNewMark(selectedNewMark);
|
||||
}
|
||||
if (w.getOldMark().getName().equals(w.getNewMark().getName())) {
|
||||
checkIfAllMarksOfControlPointAreUnchangedAndIfSoRememberThis(w.getControlPoint());
|
||||
} else {
|
||||
controlPointsNeedingReplacement.add(w.getControlPoint());
|
||||
}
|
||||
final int indexOf = controlPointDataProvider.getList().indexOf(w);
|
||||
if (indexOf != -1) {
|
||||
controlPointDataProvider.getList().set(indexOf, w);
|
||||
}
|
||||
}
|
||||
|
||||
private <T> void insert(TableWrapper<T, ? extends SetSelectionModel<T>> tableWrapper, T toInsert, boolean beforeSelection) {
|
||||
T selected = getFirstSelected(tableWrapper.getSelectionModel());
|
||||
int index = -1;
|
||||
if (tableWrapper.getDataProvider().getList().isEmpty()) {
|
||||
index = 0;
|
||||
} else if (selected != null) {
|
||||
index = tableWrapper.getDataProvider().getList().indexOf(selected) + (beforeSelection?0:1);
|
||||
}
|
||||
if (index != -1) {
|
||||
tableWrapper.getDataProvider().getList().add(index, toInsert);
|
||||
}
|
||||
}
|
||||
|
||||
private void checkIfAllMarksOfControlPointAreUnchangedAndIfSoRememberThis(ControlPointDTO controlPoint) {
|
||||
boolean allMarksUnchanged = true;
|
||||
for (ControlPointAndOldAndNewMark cpaoanb : controlPointDataProvider.getList()) {
|
||||
if (cpaoanb.getControlPoint() == controlPoint) {
|
||||
if (!cpaoanb.getOldMark().getName().equals(cpaoanb.getNewMark().getName())) {
|
||||
allMarksUnchanged = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (allMarksUnchanged) {
|
||||
controlPointsNeedingReplacement.remove(controlPoint);
|
||||
}
|
||||
}
|
||||
|
||||
private void insertWaypoint(final SailingServiceAsync sailingService, StringMessages stringMessages,
|
||||
AdminConsoleTableResources tableRes, final boolean beforeSelection) {
|
||||
new ControlPointCreationDialog(stringMessages, tableRes, marksTable.getDataProvider().getList(), new DataEntryDialog.DialogCallback<Pair<ControlPointDTO, PassingInstruction>>() {
|
||||
private void addMultiMarkControlPoint() {
|
||||
new GateCreationDialog(sailingService, errorReporter, stringMessages, tableRes,
|
||||
marks.getDataProvider().getList(), new DataEntryDialog.DialogCallback<GateDTO>() {
|
||||
@Override
|
||||
public void cancel() {
|
||||
// dialog cancelled, do nothing
|
||||
}
|
||||
public void cancel() {}
|
||||
|
||||
@Override
|
||||
public void ok(Pair<ControlPointDTO, PassingInstruction> result) {
|
||||
Set<ControlPointAndOldAndNewMark> selectedElements = controlPointsSelectionModel.getSelectedSet();
|
||||
int index = -1;
|
||||
if (controlPointDataProvider.getList().isEmpty()) {
|
||||
index = 0;
|
||||
} else if (!selectedElements.isEmpty()) {
|
||||
ControlPointAndOldAndNewMark selectedElement = selectedElements.iterator().next();
|
||||
index = controlPointDataProvider.getList().indexOf(selectedElement) + (beforeSelection?0:1);
|
||||
}
|
||||
if (index != -1) {
|
||||
for (MarkDTO markDTO : result.getA().getMarks()) {
|
||||
controlPointDataProvider.getList().add(index++, new ControlPointAndOldAndNewMark(result.getA(), result.getB(), markDTO));
|
||||
}
|
||||
}
|
||||
handleControlPointSelectionChange();
|
||||
public void ok(GateDTO result) {
|
||||
multiMarkControlPoints.dataProvider.getList().add(result);
|
||||
}
|
||||
}).show();
|
||||
}
|
||||
|
||||
private void insertWaypoint(final boolean beforeSelection) {
|
||||
List<ControlPointDTO> allControlPoints = new ArrayList<>();
|
||||
allControlPoints.addAll(multiMarkControlPoints.getDataProvider().getList());
|
||||
allControlPoints.addAll(marks.getDataProvider().getList());
|
||||
new WaypointCreationDialog(sailingService, errorReporter, stringMessages, tableRes,
|
||||
allControlPoints, new DataEntryDialog.DialogCallback<WaypointDTO>() {
|
||||
@Override
|
||||
public void cancel() {}
|
||||
|
||||
@Override
|
||||
public void ok(WaypointDTO result) {
|
||||
insert(waypoints, result, beforeSelection);
|
||||
}
|
||||
}).show();
|
||||
}
|
||||
|
||||
public abstract void refresh();
|
||||
|
||||
protected void updateWaypointTable(RaceCourseDTO raceCourseDTO) {
|
||||
List<ControlPointAndOldAndNewMark> waypointsAndOldAndNewMarks = new ArrayList<ControlPointAndOldAndNewMark>();
|
||||
for (WaypointDTO waypointDTO : raceCourseDTO.waypoints) {
|
||||
ControlPointDTO controlPointDTO = waypointDTO.controlPoint;
|
||||
for (MarkDTO mark : controlPointDTO.getMarks()) {
|
||||
ControlPointAndOldAndNewMark waypointAndOldAndNewMark = new ControlPointAndOldAndNewMark(controlPointDTO, waypointDTO.passingInstructions, mark);
|
||||
waypointsAndOldAndNewMarks.add(waypointAndOldAndNewMark);
|
||||
protected void updateWaypointsAndControlPoints(RaceCourseDTO raceCourseDTO) {
|
||||
waypoints.getDataProvider().getList().clear();
|
||||
multiMarkControlPoints.getDataProvider().getList().clear();
|
||||
waypoints.getDataProvider().getList().addAll(raceCourseDTO.waypoints);
|
||||
|
||||
Map<String, ControlPointDTO> noDuplicateCPs = new HashMap<>();
|
||||
for (ControlPointDTO controlPoint : raceCourseDTO.getControlPoints()) {
|
||||
if (controlPoint instanceof GateDTO) {
|
||||
noDuplicateCPs.put(controlPoint.getIdAsString(), controlPoint);
|
||||
}
|
||||
}
|
||||
controlPointDataProvider.getList().clear();
|
||||
controlPointDataProvider.getList().addAll(waypointsAndOldAndNewMarks);
|
||||
controlPointsNeedingReplacement.clear();
|
||||
for (ControlPointAndOldAndNewMark w : controlPointsSelectionModel.getSelectedSet()) {
|
||||
controlPointsSelectionModel.setSelected(w, false);
|
||||
}
|
||||
multiMarkControlPoints.getDataProvider().getList().addAll(noDuplicateCPs.values());
|
||||
|
||||
updateWaypointButtons();
|
||||
}
|
||||
|
||||
private void removeSelectedWaypoints(final SailingServiceAsync sailingService) {
|
||||
final Set<ControlPointDTO> selectedControlPoints = new HashSet<ControlPointDTO>();
|
||||
for (ControlPointAndOldAndNewMark cpaoanb : controlPointsSelectionModel.getSelectedSet()) {
|
||||
selectedControlPoints.add(cpaoanb.getControlPoint());
|
||||
|
||||
protected List<Util.Pair<ControlPointDTO, PassingInstruction>> createWaypointPairs() {
|
||||
List<Util.Pair<ControlPointDTO, PassingInstruction>> result = new ArrayList<>();
|
||||
for (WaypointDTO waypoint : waypoints.getDataProvider().getList()) {
|
||||
result.add(new Util.Pair<>(waypoint.controlPoint, waypoint.passingInstructions));
|
||||
}
|
||||
for (Iterator<ControlPointAndOldAndNewMark> i=controlPointDataProvider.getList().iterator(); i.hasNext(); ) {
|
||||
ControlPointAndOldAndNewMark next = i.next();
|
||||
if (selectedControlPoints.contains(next.getControlPoint())) {
|
||||
i.remove();
|
||||
controlPointsSelectionModel.setSelected(next, false);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
protected void updateWaypointButtons() {
|
||||
if (waypoints.getDataProvider().getList().isEmpty() ||
|
||||
waypoints.getSelectionModel().getSelectedObject() != null) {
|
||||
insertWaypointAfter.setEnabled(true);
|
||||
insertWaypointBefore.setEnabled(true);
|
||||
} else {
|
||||
insertWaypointBefore.setEnabled(false);
|
||||
insertWaypointAfter.setEnabled(false);
|
||||
}
|
||||
handleControlPointSelectionChange();
|
||||
}
|
||||
}
|
||||
+88
@@ -0,0 +1,88 @@
|
||||
package com.sap.sailing.gwt.ui.adminconsole;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
import com.google.gwt.user.client.ui.Grid;
|
||||
import com.google.gwt.user.client.ui.HorizontalPanel;
|
||||
import com.google.gwt.user.client.ui.Label;
|
||||
import com.google.gwt.user.client.ui.TextBox;
|
||||
import com.google.gwt.user.client.ui.Widget;
|
||||
import com.google.gwt.view.client.MultiSelectionModel;
|
||||
import com.google.gwt.view.client.SelectionChangeEvent;
|
||||
import com.google.gwt.view.client.SelectionChangeEvent.Handler;
|
||||
import com.sap.sailing.gwt.ui.client.ErrorReporter;
|
||||
import com.sap.sailing.gwt.ui.client.SailingServiceAsync;
|
||||
import com.sap.sailing.gwt.ui.client.StringMessages;
|
||||
import com.sap.sailing.gwt.ui.shared.GateDTO;
|
||||
import com.sap.sailing.gwt.ui.shared.MarkDTO;
|
||||
import com.sap.sse.gwt.client.dialog.DataEntryDialog;
|
||||
|
||||
public class GateCreationDialog extends DataEntryDialog<GateDTO> {
|
||||
private final MarkTableWrapper<MultiSelectionModel<MarkDTO>> marksWrapper;
|
||||
private final TextBox name;
|
||||
private final StringMessages stringMessages;
|
||||
|
||||
public GateCreationDialog(SailingServiceAsync sailingService, ErrorReporter errorReporter,
|
||||
final StringMessages stringMessages, AdminConsoleTableResources tableRes,
|
||||
List<MarkDTO> marks, DialogCallback<GateDTO> callback) {
|
||||
super(stringMessages.gate(), stringMessages.gate(),
|
||||
stringMessages.ok(), stringMessages.cancel(), new DataEntryDialog.Validator<GateDTO>() {
|
||||
@Override
|
||||
public String getErrorMessage(GateDTO valueToValidate) {
|
||||
if (valueToValidate == null) {
|
||||
return stringMessages.selectTwoMarksForGate();
|
||||
} else if (valueToValidate.getName() == null || valueToValidate.getName().isEmpty()) {
|
||||
return stringMessages.pleaseEnterAName();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
}, /* animationEnabled */ false, callback);
|
||||
|
||||
this.stringMessages = stringMessages;
|
||||
|
||||
name = createTextBox("");
|
||||
|
||||
marksWrapper = new MarkTableWrapper<MultiSelectionModel<MarkDTO>>(
|
||||
new MultiSelectionModel<MarkDTO>(), sailingService, stringMessages, errorReporter);
|
||||
marksWrapper.getDataProvider().getList().addAll(marks);
|
||||
|
||||
marksWrapper.getSelectionModel().addSelectionChangeHandler(new Handler() {
|
||||
@Override
|
||||
public void onSelectionChange(SelectionChangeEvent event) {
|
||||
validate();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
protected GateDTO getResult() {
|
||||
GateDTO controlPoint = null;
|
||||
Set<MarkDTO> selection = marksWrapper.getSelectionModel().getSelectedSet();
|
||||
if (selection.size() == 2) {
|
||||
name.setEnabled(true);
|
||||
Iterator<MarkDTO> i = marksWrapper.getSelectionModel().getSelectedSet().iterator();
|
||||
MarkDTO first = i.next();
|
||||
MarkDTO second = i.next();
|
||||
controlPoint = new GateDTO(/* generate UUID on the server */ null, name.getText(), first, second);
|
||||
}
|
||||
|
||||
return controlPoint;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Widget getAdditionalWidget() {
|
||||
Grid grid = new Grid(2,1);
|
||||
|
||||
HorizontalPanel nameRow = new HorizontalPanel();
|
||||
nameRow.add(new Label(stringMessages.name()));
|
||||
nameRow.add(name);
|
||||
grid.setWidget(0, 0, nameRow);
|
||||
|
||||
grid.setWidget(1, 0, marksWrapper);
|
||||
|
||||
return grid;
|
||||
}
|
||||
}
|
||||
+6
-11
@@ -1,17 +1,13 @@
|
||||
package com.sap.sailing.gwt.ui.adminconsole;
|
||||
|
||||
import java.util.Date;
|
||||
import java.util.List;
|
||||
|
||||
import com.google.gwt.user.client.Window;
|
||||
import com.google.gwt.user.client.rpc.AsyncCallback;
|
||||
import com.sap.sailing.domain.common.PassingInstruction;
|
||||
import com.sap.sailing.domain.common.impl.Util.Pair;
|
||||
import com.sap.sailing.gwt.ui.client.ErrorReporter;
|
||||
import com.sap.sailing.gwt.ui.client.RegattaRefresher;
|
||||
import com.sap.sailing.gwt.ui.client.SailingServiceAsync;
|
||||
import com.sap.sailing.gwt.ui.client.StringMessages;
|
||||
import com.sap.sailing.gwt.ui.shared.ControlPointDTO;
|
||||
import com.sap.sailing.gwt.ui.shared.RaceCourseDTO;
|
||||
|
||||
/**
|
||||
@@ -30,10 +26,9 @@ public class RaceCourseManagementPanel extends AbstractRaceManagementPanel {
|
||||
super(sailingService, errorReporter, regattaRefresher, stringMessages);
|
||||
|
||||
courseManagementWidget = new CourseManagementWidget(sailingService, errorReporter, stringMessages) {
|
||||
|
||||
@Override
|
||||
protected void saveCourse(List<Pair<ControlPointDTO, PassingInstruction>> controlPoints) {
|
||||
sailingService.updateRaceCourse(singleSelectedRace, controlPoints, new AsyncCallback<Void>() {
|
||||
protected void save() {
|
||||
sailingService.updateRaceCourse(singleSelectedRace, createWaypointPairs(), new AsyncCallback<Void>() {
|
||||
@Override
|
||||
public void onFailure(Throwable caught) {
|
||||
errorReporter.reportError(stringMessages.errorUpdatingRaceCourse(caught.getMessage()));
|
||||
@@ -50,13 +45,13 @@ public class RaceCourseManagementPanel extends AbstractRaceManagementPanel {
|
||||
@Override
|
||||
public void refresh() {
|
||||
if (singleSelectedRace != null && selectedRaceDTO != null) {
|
||||
// courseActionsPanel.setVisible(true);
|
||||
mainPanel.setVisible(true);
|
||||
// TODO bug 1351: never use System.currentTimeMillis() on the client when trying to compare anything with "server time"; this one is not so urgent as it is reached only in the AdminConsole and we expect administrators to have proper client-side time settings
|
||||
sailingService.getRaceCourse(singleSelectedRace, new Date(), new AsyncCallback<RaceCourseDTO>() {
|
||||
@Override
|
||||
public void onSuccess(RaceCourseDTO raceCourseDTO) {
|
||||
updateWaypointTable(raceCourseDTO);
|
||||
marksTable.refresh(raceCourseDTO.getMarks());
|
||||
updateWaypointsAndControlPoints(raceCourseDTO);
|
||||
marks.refresh(raceCourseDTO.getMarks());
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -67,7 +62,7 @@ public class RaceCourseManagementPanel extends AbstractRaceManagementPanel {
|
||||
}
|
||||
});
|
||||
} else {
|
||||
courseActionsPanel.setVisible(false);
|
||||
mainPanel.setVisible(false);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
+8
-14
@@ -1,7 +1,6 @@
|
||||
package com.sap.sailing.gwt.ui.adminconsole;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
import com.google.gwt.cell.client.FieldUpdater;
|
||||
import com.google.gwt.event.dom.client.ClickEvent;
|
||||
@@ -9,13 +8,10 @@ import com.google.gwt.event.dom.client.ClickHandler;
|
||||
import com.google.gwt.user.client.rpc.AsyncCallback;
|
||||
import com.google.gwt.user.client.ui.Button;
|
||||
import com.google.gwt.user.client.ui.Panel;
|
||||
import com.sap.sailing.domain.common.PassingInstruction;
|
||||
import com.sap.sailing.domain.common.dto.PositionDTO;
|
||||
import com.sap.sailing.domain.common.impl.Util.Pair;
|
||||
import com.sap.sailing.gwt.ui.client.ErrorReporter;
|
||||
import com.sap.sailing.gwt.ui.client.SailingServiceAsync;
|
||||
import com.sap.sailing.gwt.ui.client.StringMessages;
|
||||
import com.sap.sailing.gwt.ui.shared.ControlPointDTO;
|
||||
import com.sap.sailing.gwt.ui.shared.MarkDTO;
|
||||
import com.sap.sailing.gwt.ui.shared.RaceCourseDTO;
|
||||
import com.sap.sse.gwt.client.dialog.DataEntryDialog;
|
||||
@@ -51,7 +47,7 @@ public class RaceLogTrackingCourseDefinitionDialog extends RaceLogTrackingDialog
|
||||
}).show();
|
||||
}
|
||||
});
|
||||
courseActionsPanel.insert(addMark, courseActionsPanel.getWidgetIndex(RaceLogCourseManagementWidget.this.saveButton));
|
||||
marksBtnsPanel.add(addMark);
|
||||
|
||||
|
||||
Button cancel = new Button(stringMessages.cancel());
|
||||
@@ -61,7 +57,7 @@ public class RaceLogTrackingCourseDefinitionDialog extends RaceLogTrackingDialog
|
||||
hide();
|
||||
}
|
||||
});
|
||||
courseActionsPanel.insert(cancel, courseActionsPanel.getWidgetIndex(RaceLogCourseManagementWidget.this.saveButton));
|
||||
buttonsPanel.add(cancel);
|
||||
|
||||
ImagesBarColumn<MarkDTO, RaceLogTrackingCourseDefinitionDialogMarksImagesBarCell> actionColumn =
|
||||
new ImagesBarColumn<MarkDTO, RaceLogTrackingCourseDefinitionDialogMarksImagesBarCell>(
|
||||
@@ -96,12 +92,13 @@ public class RaceLogTrackingCourseDefinitionDialog extends RaceLogTrackingDialog
|
||||
}
|
||||
}
|
||||
});
|
||||
marksTable.getTable().addColumn(actionColumn);
|
||||
marks.getTable().addColumn(actionColumn);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void saveCourse(List<Pair<ControlPointDTO, PassingInstruction>> controlPoints) {
|
||||
sailingService.addCourseDefinitionToRaceLog(leaderboardName, raceColumnName, fleetName, controlPoints, new AsyncCallback<Void>() {
|
||||
protected void save() {
|
||||
sailingService.addCourseDefinitionToRaceLog(leaderboardName, raceColumnName, fleetName,
|
||||
createWaypointPairs(), new AsyncCallback<Void>() {
|
||||
@Override
|
||||
public void onSuccess(Void result) {
|
||||
hide();
|
||||
@@ -119,10 +116,7 @@ public class RaceLogTrackingCourseDefinitionDialog extends RaceLogTrackingDialog
|
||||
sailingService.getLastCourseDefinitionInRaceLog(leaderboardName, raceColumnName, fleetName, new AsyncCallback<RaceCourseDTO>() {
|
||||
@Override
|
||||
public void onSuccess(RaceCourseDTO result) {
|
||||
updateWaypointTable(result);
|
||||
if (result.waypoints.isEmpty()) {
|
||||
insertWaypointBefore.setEnabled(true);
|
||||
}
|
||||
updateWaypointsAndControlPoints(result);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -134,7 +128,7 @@ public class RaceLogTrackingCourseDefinitionDialog extends RaceLogTrackingDialog
|
||||
sailingService.getMarksInRaceLog(leaderboardName, raceColumnName, fleetName, new AsyncCallback<Collection<MarkDTO>>() {
|
||||
@Override
|
||||
public void onSuccess(Collection<MarkDTO> result) {
|
||||
marksTable.refresh(result);
|
||||
marks.refresh(result);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
+9
-1
@@ -1,5 +1,7 @@
|
||||
package com.sap.sailing.gwt.ui.adminconsole;
|
||||
|
||||
import java.util.Collection;
|
||||
|
||||
import com.google.gwt.core.client.GWT;
|
||||
import com.google.gwt.user.cellview.client.CellTable;
|
||||
import com.google.gwt.user.client.ui.IsWidget;
|
||||
@@ -55,4 +57,10 @@ public abstract class TableWrapper<T, S extends SelectionModel<T>> implements Is
|
||||
public ListDataProvider<T> getDataProvider() {
|
||||
return dataProvider;
|
||||
}
|
||||
}
|
||||
|
||||
public void refresh(Collection<T> newItems) {
|
||||
dataProvider.getList().clear();
|
||||
dataProvider.getList().addAll(newItems);
|
||||
dataProvider.flush();
|
||||
}
|
||||
}
|
||||
+108
@@ -0,0 +1,108 @@
|
||||
package com.sap.sailing.gwt.ui.adminconsole;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import com.google.gwt.user.client.ui.Grid;
|
||||
import com.google.gwt.user.client.ui.HorizontalPanel;
|
||||
import com.google.gwt.user.client.ui.Label;
|
||||
import com.google.gwt.user.client.ui.ListBox;
|
||||
import com.google.gwt.user.client.ui.Widget;
|
||||
import com.google.gwt.view.client.SelectionChangeEvent;
|
||||
import com.google.gwt.view.client.SingleSelectionModel;
|
||||
import com.google.gwt.view.client.SelectionChangeEvent.Handler;
|
||||
import com.sap.sailing.domain.common.PassingInstruction;
|
||||
import com.sap.sailing.domain.common.impl.Util;
|
||||
import com.sap.sailing.gwt.ui.client.ErrorReporter;
|
||||
import com.sap.sailing.gwt.ui.client.SailingServiceAsync;
|
||||
import com.sap.sailing.gwt.ui.client.StringMessages;
|
||||
import com.sap.sailing.gwt.ui.shared.ControlPointDTO;
|
||||
import com.sap.sailing.gwt.ui.shared.MarkDTO;
|
||||
import com.sap.sailing.gwt.ui.shared.WaypointDTO;
|
||||
import com.sap.sse.gwt.client.dialog.DataEntryDialog;
|
||||
|
||||
public class WaypointCreationDialog extends DataEntryDialog<WaypointDTO> {
|
||||
private final ControlPointTableWrapper<SingleSelectionModel<ControlPointDTO>> controlPointsWrapper;
|
||||
private final ListBox passingInstructions;
|
||||
private final StringMessages stringMessages;
|
||||
|
||||
public WaypointCreationDialog(SailingServiceAsync sailingService, ErrorReporter errorReporter,
|
||||
final StringMessages stringMessages, AdminConsoleTableResources tableRes,
|
||||
List<ControlPointDTO> controlPoints, DialogCallback<WaypointDTO> callback) {
|
||||
super(stringMessages.waypoint(), stringMessages.waypoint(),
|
||||
stringMessages.ok(), stringMessages.cancel(), new DataEntryDialog.Validator<WaypointDTO>() {
|
||||
@Override
|
||||
public String getErrorMessage(WaypointDTO valueToValidate) {
|
||||
if (valueToValidate.controlPoint == null) {
|
||||
return stringMessages.pleaseSelectAControlPoint();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
}, /* animationEnabled */ false, callback);
|
||||
|
||||
this.stringMessages = stringMessages;
|
||||
|
||||
controlPointsWrapper = new ControlPointTableWrapper<SingleSelectionModel<ControlPointDTO>>(
|
||||
new SingleSelectionModel<ControlPointDTO>(), sailingService, stringMessages, errorReporter);
|
||||
controlPointsWrapper.getDataProvider().getList().addAll(controlPoints);
|
||||
|
||||
passingInstructions = createListBox(false);
|
||||
updatePassingInstructions();
|
||||
|
||||
controlPointsWrapper.getSelectionModel().addSelectionChangeHandler(new Handler() {
|
||||
@Override
|
||||
public void onSelectionChange(SelectionChangeEvent event) {
|
||||
updatePassingInstructions();
|
||||
validate();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void updatePassingInstructions() {
|
||||
passingInstructions.clear();
|
||||
|
||||
int numMarks = controlPointsWrapper.getSelectionModel().getSelectedObject() != null ?
|
||||
Util.size(controlPointsWrapper.getSelectionModel().getSelectedObject().getMarks()) : 0;
|
||||
|
||||
int i = 0;
|
||||
passingInstructions.insertItem(PassingInstruction.None.name(), i++);
|
||||
for (PassingInstruction pi : PassingInstruction.relevantValues()) {
|
||||
for (int numApplicableMarks : pi.applicability) {
|
||||
if (numApplicableMarks == numMarks) {
|
||||
passingInstructions.insertItem(pi.name(), i++);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected WaypointDTO getResult() {
|
||||
PassingInstruction pi = passingInstructions.getSelectedIndex() > 0 ?
|
||||
PassingInstruction.valueOf(passingInstructions.getItemText(passingInstructions.getSelectedIndex()))
|
||||
: PassingInstruction.None;
|
||||
|
||||
ControlPointDTO controlPoint = controlPointsWrapper.getSelectionModel().getSelectedObject();
|
||||
List<MarkDTO> marks = new ArrayList<MarkDTO>();
|
||||
String name = null;
|
||||
if (controlPoint != null) {
|
||||
Util.addAll(controlPoint.getMarks(), marks);
|
||||
name = controlPoint.getName();
|
||||
}
|
||||
return new WaypointDTO(name, controlPoint, marks, pi);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Widget getAdditionalWidget() {
|
||||
Grid grid = new Grid(2,1);
|
||||
|
||||
grid.setWidget(0, 0, controlPointsWrapper);
|
||||
|
||||
HorizontalPanel passingInstructionsRow = new HorizontalPanel();
|
||||
grid.setWidget(1, 0, passingInstructionsRow);
|
||||
passingInstructionsRow.add(new Label(stringMessages.passingInstructions() + ":"));
|
||||
passingInstructionsRow.add(passingInstructions);
|
||||
|
||||
return grid;
|
||||
}
|
||||
}
|
||||
+51
@@ -0,0 +1,51 @@
|
||||
package com.sap.sailing.gwt.ui.adminconsole;
|
||||
|
||||
import com.google.gwt.user.cellview.client.TextColumn;
|
||||
import com.google.gwt.view.client.SelectionModel;
|
||||
import com.sap.sailing.gwt.ui.client.ErrorReporter;
|
||||
import com.sap.sailing.gwt.ui.client.SailingServiceAsync;
|
||||
import com.sap.sailing.gwt.ui.client.StringMessages;
|
||||
import com.sap.sailing.gwt.ui.shared.ControlPointDTO;
|
||||
import com.sap.sailing.gwt.ui.shared.GateDTO;
|
||||
import com.sap.sailing.gwt.ui.shared.MarkDTO;
|
||||
import com.sap.sailing.gwt.ui.shared.WaypointDTO;
|
||||
|
||||
public class WaypointTableWrapper<S extends SelectionModel<WaypointDTO>> extends TableWrapper<WaypointDTO, S> {
|
||||
public WaypointTableWrapper(S selectionModel, SailingServiceAsync sailingService, final StringMessages stringMessages,
|
||||
ErrorReporter errorReporter) {
|
||||
super(sailingService, stringMessages, errorReporter, selectionModel);
|
||||
|
||||
mainPanel.add(table);
|
||||
|
||||
TextColumn<WaypointDTO> nameColumn = new TextColumn<WaypointDTO>() {
|
||||
@Override
|
||||
public String getValue(WaypointDTO d) {
|
||||
return d.controlPoint.getName();
|
||||
}
|
||||
};
|
||||
table.addColumn(nameColumn, stringMessages.controlPoint() + " " + stringMessages.name());
|
||||
|
||||
TextColumn<WaypointDTO> typeColumn = new TextColumn<WaypointDTO>() {
|
||||
@Override
|
||||
public String getValue(WaypointDTO w) {
|
||||
ControlPointDTO d = w.controlPoint;
|
||||
if (d instanceof GateDTO) {
|
||||
return "2x " + stringMessages.mark();
|
||||
} else if (d instanceof MarkDTO) {
|
||||
return stringMessages.mark();
|
||||
} else {
|
||||
return stringMessages.unknown();
|
||||
}
|
||||
}
|
||||
};
|
||||
table.addColumn(typeColumn, stringMessages.type());
|
||||
|
||||
TextColumn<WaypointDTO> passingInstructionsColumn = new TextColumn<WaypointDTO>() {
|
||||
@Override
|
||||
public String getValue(WaypointDTO waypoint) {
|
||||
return waypoint.passingInstructions != null ? waypoint.passingInstructions.name() : "";
|
||||
}
|
||||
};
|
||||
table.addColumn(passingInstructionsColumn, stringMessages.passingInstructions());
|
||||
}
|
||||
}
|
||||
+4
-1
@@ -364,11 +364,12 @@ public interface StringMessages extends Messages {
|
||||
String controlPoint();
|
||||
String errorUpdatingRaceCourse(String message);
|
||||
String successfullyUpdatedCourse();
|
||||
String selectOneMarkOrTwoMarksForGate();
|
||||
String selectTwoMarksForGate();
|
||||
String errorTryingToObtainTheMarksOfTheRace(String message);
|
||||
String errorTryingToObtainRaceCourse(String message);
|
||||
String insertWaypointBeforeSelected();
|
||||
String insertWaypointAfterSelected();
|
||||
String addGate();
|
||||
String scoringSchemeLowPointSystem();
|
||||
String scoringSchemeHighPointSystem();
|
||||
String scoringSchemeLowPointWinnerGetsZero();
|
||||
@@ -1007,4 +1008,6 @@ public interface StringMessages extends Messages {
|
||||
String authorPriority();
|
||||
String removeDenotation();
|
||||
String competitorRegistrationsMissingProceed(String namesOfRaces);
|
||||
String pleaseSelectAControlPoint();
|
||||
String twoMarkControlPoint();
|
||||
}
|
||||
+5
-2
@@ -389,11 +389,12 @@ newMark=New Mark
|
||||
controlPoint=Mark/Gate
|
||||
errorUpdatingRaceCourse=Error updating race course: {0}
|
||||
successfullyUpdatedCourse=Successfully updated race course
|
||||
selectOneMarkOrTwoMarksForGate=Select a single mark or two marks to create a gate
|
||||
selectTwoMarksForGate=Select two marks to create a gate
|
||||
errorTryingToObtainTheMarksOfTheRace=Error trying to obtain the marks of the race course: {0}
|
||||
errorTryingToObtainRaceCourse=Error trying to obtain the race course: {0}
|
||||
insertWaypointBeforeSelected=Insert waypoint before selected
|
||||
insertWaypointAfterSelected=Insert waypoint after selected
|
||||
addGate=Add Gate
|
||||
scoringSchemeLowPointSystem=Low Point System
|
||||
scoringSchemeHighPointSystem=High Point System
|
||||
scoringSchemeHighPointEssOverall=High Point System ESS Overall
|
||||
@@ -992,4 +993,6 @@ importWindTooltip=Unchecking this option will drastically lower the amount of da
|
||||
authorName=Author name
|
||||
authorPriority=Author priority
|
||||
removeDenotation=Remove Denotation
|
||||
competitorRegistrationsMissingProceed=At least one of the selected races ({0}) is missing competitor registrations. Proceed anyway?
|
||||
competitorRegistrationsMissingProceed=At least one of the selected races ({0}) is missing competitor registrations. Proceed anyway?
|
||||
pleaseSelectAControlPoint=Please select a control point
|
||||
twoMarkControlPoint=2-mark-controlpoint
|
||||
+5
-2
@@ -390,11 +390,12 @@ newMark=Neue Marke
|
||||
controlPoint=Einzelmarke/Gate
|
||||
errorUpdatingRaceCourse=Fehler beim Aktualisieren des neuen Kurses: {0}
|
||||
successfullyUpdatedCourse=Kurs erfolgreich aktualisiert
|
||||
selectOneMarkOrTwoMarksForGate=Eine einzelne Marke auswählen oder zwei Marken, um ein Gate zu erstellen
|
||||
selectTwoMarksForGate=Zwei Marken auswählen, um ein Gate zu erstellen
|
||||
errorTryingToObtainTheMarksOfTheRace=Fehler beim Ermitteln der Marken des Regattakurses: {0}
|
||||
errorTryingToObtainRaceCourse=Fehler beim Ermitteln des Rennkurses: {0}
|
||||
insertWaypointBeforeSelected=Wegpunkt nach dem selektierten einfügen
|
||||
insertWaypointAfterSelected=Wegpunkt vor dem selektierten einfügen
|
||||
addGate=Gate hinzufügen
|
||||
scoringSchemeLowPointSystem=Low Point System
|
||||
scoringSchemeHighPointSystem=High Point System
|
||||
scoringSchemeHighPointEssOverall=High Point System ESS Gesamtwertung
|
||||
@@ -988,4 +989,6 @@ importWindTooltip=Diese Option zu deselektieren führt zu einer wesentlich klein
|
||||
authorName=Benutzername
|
||||
authorPriority=Benutzer-Priorität
|
||||
removeDenotation=Markierung entfernen
|
||||
competitorRegistrationsMissingProceed=Für mindestens eins der Rennen ({0}) sind keine Teams registriert. Trotzdem fortfahren?
|
||||
competitorRegistrationsMissingProceed=Für mindestens eins der Rennen ({0}) sind keine Teams registriert. Trotzdem fortfahren?
|
||||
pleaseSelectAControlPoint=Bitte eine Einzelmark/ein Gate auswählen
|
||||
twoMarkControlPoint=2-Marken-Kontrollpunkt
|
||||
+36
-20
@@ -160,6 +160,7 @@ import com.sap.sailing.domain.common.impl.WindSourceImpl;
|
||||
import com.sap.sailing.domain.common.racelog.FlagPole;
|
||||
import com.sap.sailing.domain.common.racelog.Flags;
|
||||
import com.sap.sailing.domain.common.racelog.RaceLogRaceStatus;
|
||||
import com.sap.sailing.domain.common.racelog.RacingProcedureType;
|
||||
import com.sap.sailing.domain.common.racelog.tracking.NoCorrespondingServiceRegisteredException;
|
||||
import com.sap.sailing.domain.common.racelog.tracking.NotDenotedForRaceLogTrackingException;
|
||||
import com.sap.sailing.domain.common.racelog.tracking.NotRevokableException;
|
||||
@@ -167,7 +168,6 @@ import com.sap.sailing.domain.common.racelog.tracking.RaceLogTrackingState;
|
||||
import com.sap.sailing.domain.common.racelog.tracking.TransformationException;
|
||||
import com.sap.sailing.domain.common.racelog.tracking.TypeBasedServiceFinder;
|
||||
import com.sap.sailing.domain.common.racelog.tracking.TypeBasedServiceFinderFactory;
|
||||
import com.sap.sailing.domain.common.racelog.RacingProcedureType;
|
||||
import com.sap.sailing.domain.igtimiadapter.Account;
|
||||
import com.sap.sailing.domain.igtimiadapter.IgtimiConnection;
|
||||
import com.sap.sailing.domain.igtimiadapter.IgtimiConnectionFactory;
|
||||
@@ -1633,6 +1633,7 @@ public class SailingServiceImpl extends ProxiedRemoteServiceServlet implements S
|
||||
@Override
|
||||
public RaceCourseDTO getRaceCourse(RegattaAndRaceIdentifier raceIdentifier, Date date) {
|
||||
List<WaypointDTO> waypointDTOs = new ArrayList<WaypointDTO>();
|
||||
Map<Serializable, ControlPointDTO> controlPointCache = new HashMap<>();
|
||||
RaceCourseDTO result = new RaceCourseDTO(waypointDTOs);
|
||||
if (date != null) {
|
||||
TimePoint dateAsTimePoint = new MillisecondsTimePoint(date);
|
||||
@@ -1640,14 +1641,18 @@ public class SailingServiceImpl extends ProxiedRemoteServiceServlet implements S
|
||||
if (trackedRace != null) {
|
||||
Course course = trackedRace.getRace().getCourse();
|
||||
for (Waypoint waypoint : course.getWaypoints()) {
|
||||
List<MarkDTO> markDTOs = new ArrayList<MarkDTO>();
|
||||
for (Mark mark : trackedRace.getMarks()) {
|
||||
List<MarkDTO> marks = new ArrayList<>();
|
||||
for (Mark mark : waypoint.getMarks()) {
|
||||
GPSFixTrack<Mark, GPSFix> track = trackedRace.getOrCreateTrack(mark);
|
||||
Position positionAtDate = track.getEstimatedPosition(dateAsTimePoint, /* extrapolate */false);
|
||||
markDTOs.add(convertToMarkDTO(mark, positionAtDate));
|
||||
marks.add(convertToMarkDTO(mark, positionAtDate));
|
||||
}
|
||||
ControlPointDTO controlPointDTO = convertToControlPointDTO(waypoint.getControlPoint(), trackedRace, dateAsTimePoint);
|
||||
WaypointDTO waypointDTO = new WaypointDTO(waypoint.getName(), controlPointDTO, markDTOs, waypoint.getPassingInstructions());
|
||||
ControlPointDTO controlPointDTO = controlPointCache.get(waypoint.getControlPoint().getId());
|
||||
if (controlPointDTO == null) {
|
||||
controlPointDTO = convertToControlPointDTO(waypoint.getControlPoint(), trackedRace, dateAsTimePoint);
|
||||
controlPointCache.put(waypoint.getControlPoint().getId(), controlPointDTO);
|
||||
}
|
||||
WaypointDTO waypointDTO = new WaypointDTO(waypoint.getName(), controlPointDTO, marks, waypoint.getPassingInstructions());
|
||||
waypointDTOs.add(waypointDTO);
|
||||
}
|
||||
}
|
||||
@@ -1685,29 +1690,34 @@ public class SailingServiceImpl extends ProxiedRemoteServiceServlet implements S
|
||||
|
||||
/**
|
||||
* For each {@link ControlPointDTO} in <code>controlPoints</code> tries to find the best-matching waypoint
|
||||
* from the {@code old} {@code CourseBase}.
|
||||
* from the {@code old} {@code CourseBase}, and also from the newly created additional waypoints.
|
||||
* If such a waypoint is found, its control point is added to the control point list for the new course.
|
||||
* Otherwise, a new control point is created using the default {@link com.sap.sailing.domain.base.DomainFactory}
|
||||
* instance.
|
||||
*/
|
||||
private List<Pair<ControlPoint, PassingInstruction>> resolveControlPoints(
|
||||
CourseBase old, List<Pair<ControlPointDTO, PassingInstruction>> controlPoints) {
|
||||
Map<ControlPointDTO, ControlPoint> newlyCreatedCache = new HashMap<ControlPointDTO, ControlPoint>();
|
||||
Iterable<Waypoint> waypoints = old.getWaypoints();
|
||||
List<Pair<ControlPoint, PassingInstruction>> newControlPoints = new ArrayList<Pair<ControlPoint, PassingInstruction>>();
|
||||
int lastMatchPosition = -1;
|
||||
for (Pair<ControlPointDTO, PassingInstruction> controlPointAndPassingInstruction : controlPoints) {
|
||||
ControlPointDTO controlPointDTO = controlPointAndPassingInstruction.getA();
|
||||
ControlPoint matchFromOldCourse = null;
|
||||
for (int i=lastMatchPosition+1; matchFromOldCourse == null && i<Util.size(waypoints); i++) {
|
||||
Waypoint waypointAtI = Util.get(waypoints, i);
|
||||
ControlPoint controlPointAtI = waypointAtI.getControlPoint();
|
||||
if (controlPointAtI.getId().toString().equals(controlPointDTO.getIdAsString()) && markIDsMatch(controlPointAtI.getMarks(), controlPointDTO.getMarks())) {
|
||||
matchFromOldCourse = controlPointAtI;
|
||||
newControlPoints.add(new Pair<ControlPoint, PassingInstruction>(matchFromOldCourse, null));
|
||||
lastMatchPosition = i;
|
||||
ControlPoint match = null;
|
||||
if (newlyCreatedCache.containsKey(controlPointDTO)) {
|
||||
match = newlyCreatedCache.get(controlPointDTO);
|
||||
} else {
|
||||
for (Waypoint oldWP : waypoints) {
|
||||
ControlPoint oldControlPoint = oldWP.getControlPoint();
|
||||
if (oldControlPoint.getId().toString().equals(controlPointDTO.getIdAsString())
|
||||
&& markIDsMatch(oldControlPoint.getMarks(), controlPointDTO.getMarks())) {
|
||||
match = oldControlPoint;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (matchFromOldCourse == null) {
|
||||
if (match != null) {
|
||||
newControlPoints.add(new Pair<ControlPoint, PassingInstruction>(match, controlPointAndPassingInstruction.getB()));
|
||||
} else {
|
||||
// no match found; create new control point:
|
||||
ControlPoint newControlPoint;
|
||||
if (controlPointDTO instanceof GateDTO) {
|
||||
@@ -1727,6 +1737,7 @@ public class SailingServiceImpl extends ProxiedRemoteServiceServlet implements S
|
||||
PassingInstruction passingInstructions = controlPointAndPassingInstruction.getB();
|
||||
newControlPoints.add(new Pair<ControlPoint, PassingInstruction>(newControlPoint, passingInstructions));
|
||||
}
|
||||
newlyCreatedCache.put(controlPointDTO, newControlPoint);
|
||||
}
|
||||
}
|
||||
return newControlPoints;
|
||||
@@ -4170,8 +4181,12 @@ public class SailingServiceImpl extends ProxiedRemoteServiceServlet implements S
|
||||
raceLog.add(event);
|
||||
}
|
||||
|
||||
private WaypointDTO convertToWaypointDTO(Waypoint waypoint) {
|
||||
ControlPointDTO cp = convertToControlPointDTO(waypoint.getControlPoint());
|
||||
private WaypointDTO convertToWaypointDTO(Waypoint waypoint, Map<Serializable, ControlPointDTO> controlPointCache) {
|
||||
ControlPointDTO cp = controlPointCache.get(waypoint.getControlPoint().getId());
|
||||
if (cp == null) {
|
||||
cp = convertToControlPointDTO(waypoint.getControlPoint());
|
||||
controlPointCache.put(waypoint.getControlPoint().getId(), cp);
|
||||
}
|
||||
List<MarkDTO> marks = new ArrayList<MarkDTO>();
|
||||
Util.addAll(cp.getMarks(), marks);
|
||||
return new WaypointDTO(waypoint.getName(), cp, marks, waypoint.getPassingInstructions());
|
||||
@@ -4179,9 +4194,10 @@ public class SailingServiceImpl extends ProxiedRemoteServiceServlet implements S
|
||||
|
||||
private RaceCourseDTO convertToRaceCourseDTO(CourseBase course) {
|
||||
List<WaypointDTO> waypointDTOs = new ArrayList<WaypointDTO>();
|
||||
Map<Serializable, ControlPointDTO> controlPointCache = new HashMap<>();
|
||||
RaceCourseDTO result = new RaceCourseDTO(waypointDTOs);
|
||||
for (Waypoint waypoint : course.getWaypoints()) {
|
||||
waypointDTOs.add(convertToWaypointDTO(waypoint));
|
||||
waypointDTOs.add(convertToWaypointDTO(waypoint, controlPointCache));
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@@ -28,4 +28,18 @@ public class MarkDTO extends ControlPointDTO {
|
||||
public Iterable<MarkDTO> getMarks() {
|
||||
return Collections.singleton(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof MarkDTO) {
|
||||
MarkDTO other = (MarkDTO) o;
|
||||
return getIdAsString() != null && getIdAsString().equals(other.getIdAsString());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return getIdAsString().hashCode();
|
||||
}
|
||||
}
|
||||
+10
@@ -10,11 +10,17 @@ import com.google.gwt.user.client.rpc.IsSerializable;
|
||||
|
||||
public class RaceCourseDTO implements IsSerializable {
|
||||
public List<WaypointDTO> waypoints;
|
||||
public List<MarkDTO> marks;
|
||||
|
||||
RaceCourseDTO() {}
|
||||
|
||||
public RaceCourseDTO(List<WaypointDTO> waypoints) {
|
||||
this(waypoints, null);
|
||||
}
|
||||
|
||||
public RaceCourseDTO(List<WaypointDTO> waypoints, List<MarkDTO> marks) {
|
||||
this.waypoints = waypoints;
|
||||
this.marks = marks;
|
||||
}
|
||||
|
||||
public List<ControlPointDTO> getControlPoints() {
|
||||
@@ -26,6 +32,10 @@ public class RaceCourseDTO implements IsSerializable {
|
||||
}
|
||||
|
||||
public Collection<MarkDTO> getMarks() {
|
||||
if (marks != null) {
|
||||
return marks;
|
||||
}
|
||||
|
||||
Map<String, MarkDTO> marks = new HashMap<String, MarkDTO>();
|
||||
for(WaypointDTO waypoint: waypoints) {
|
||||
for(MarkDTO mark: waypoint.marks) {
|
||||
|
||||
+14
@@ -5,6 +5,10 @@ import java.util.List;
|
||||
import com.sap.sailing.domain.common.PassingInstruction;
|
||||
import com.sap.sailing.domain.common.dto.NamedDTO;
|
||||
|
||||
/**
|
||||
* Equality and hashcode based on object identity
|
||||
*
|
||||
*/
|
||||
public class WaypointDTO extends NamedDTO {
|
||||
private static final long serialVersionUID = 7439553659782967746L;
|
||||
|
||||
@@ -23,4 +27,14 @@ public class WaypointDTO extends NamedDTO {
|
||||
this.controlPoint = controlPoint;
|
||||
this.passingInstructions = passingInstructions;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object obj) {
|
||||
return this == obj;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return System.identityHashCode(this);
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user