diff options
31 files changed, 1530 insertions, 124 deletions
diff --git a/client/src/main/java/com/vaadin/client/connectors/JavaScriptRendererConnector.java b/client/src/main/java/com/vaadin/client/connectors/JavaScriptRendererConnector.java index 90ced5e095..3191be2ed1 100644 --- a/client/src/main/java/com/vaadin/client/connectors/JavaScriptRendererConnector.java +++ b/client/src/main/java/com/vaadin/client/connectors/JavaScriptRendererConnector.java @@ -17,6 +17,7 @@ package com.vaadin.client.connectors; import java.util.ArrayList; import java.util.Collection; +import java.util.logging.Logger; import com.google.gwt.core.client.JavaScriptObject; import com.google.gwt.core.client.JsArrayString; @@ -64,7 +65,7 @@ public class JavaScriptRendererConnector private static native JavaScriptObject createCellReferenceWrapper() /*-{ var reference = {}; - + var setProperty = function(name, getter, setter) { var descriptor = { get: getter @@ -74,25 +75,25 @@ public class JavaScriptRendererConnector } Object.defineProperty(reference, name, descriptor); }; - + setProperty("element", function() { return reference.target.@CellReference::getElement()(); }, null); - + setProperty("rowIndex", function() { return reference.target.@CellReference::getRowIndex()(); }, null); - + setProperty("columnIndex", function() { return reference.target.@CellReference::getColumnIndex()(); }, null); - + setProperty("colSpan", function() { return reference.target.@RendererCellReference::getColSpan()(); }, function(colSpan) { reference.target.@RendererCellReference::setColSpan(*)(colSpan); }); - + return reference; }-*/; @@ -136,8 +137,15 @@ public class JavaScriptRendererConnector + " must have a function named 'render'"); } + if (hasFunction("destory")) { + getLogger().severe("Your JavaScript connector (" + + helper.getInitFunctionName() + + ") has a typo. The destory method should be renamed to destroy."); + } + final boolean hasInit = hasFunction("init"); - final boolean hasDestroy = hasFunction("destroy"); + final boolean hasDestroy = hasFunction("destroy") + || hasFunction("destory"); final boolean hasOnActivate = hasFunction("onActivate"); final boolean hasGetConsumedEvents = hasFunction("getConsumedEvents"); final boolean hasOnBrowserEvent = hasFunction("onBrowserEvent"); @@ -183,17 +191,23 @@ public class JavaScriptRendererConnector @Override public void destroy(RendererCellReference cell) { + getLogger().warning("Destprying: " + cell.getRowIndex() + " " + + cell.getColumnIndexDOM()); if (hasDestroy) { - destory(helper.getConnectorWrapper(), getJsCell(cell)); + destroy(helper.getConnectorWrapper(), getJsCell(cell)); } else { super.destroy(cell); } } - private native void destory(JavaScriptObject wrapper, + private native void destroy(JavaScriptObject wrapper, JavaScriptObject cell) /*-{ - wrapper.destory(cell); + if (wrapper.destroy) { + wrapper.destroy(cell); + } else if (wrapper.destory) { + wrapper.destory(cell); + } }-*/; @Override @@ -258,6 +272,10 @@ public class JavaScriptRendererConnector }; } + private Logger getLogger() { + return Logger.getLogger(JavaScriptRendererConnector.class.getName()); + } + @Override public Object decode(JsonValue value) { // Let the js logic decode the raw json that the server sent diff --git a/client/src/main/java/com/vaadin/client/renderers/ImageRenderer.java b/client/src/main/java/com/vaadin/client/renderers/ImageRenderer.java index d1195969da..955a0c4cb2 100644 --- a/client/src/main/java/com/vaadin/client/renderers/ImageRenderer.java +++ b/client/src/main/java/com/vaadin/client/renderers/ImageRenderer.java @@ -29,7 +29,7 @@ import com.vaadin.client.widget.grid.RendererCellReference; */ public class ImageRenderer extends ClickableRenderer<String, Image> { - public static final String TRANSPARENT_GIF_1PX = "data:image/gif;base64,R0lGODlhAQABAIAAAP///wAAACwAAAAAAQABAAACAkQBADs="; + public static final String TRANSPARENT_GIF_1PX = "data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7"; @Override public Image createWidget() { diff --git a/client/src/main/java/com/vaadin/client/ui/VComboBox.java b/client/src/main/java/com/vaadin/client/ui/VComboBox.java index 4cf7ab8856..d0de766a55 100644 --- a/client/src/main/java/com/vaadin/client/ui/VComboBox.java +++ b/client/src/main/java/com/vaadin/client/ui/VComboBox.java @@ -87,7 +87,7 @@ import com.vaadin.shared.util.SharedUtil; * Client side implementation of the ComboBox component. * * TODO needs major refactoring (to be extensible etc) - * + * * @since 8.0 */ @SuppressWarnings("deprecation") @@ -243,12 +243,12 @@ public class VComboBox extends Composite implements Field, KeyDownHandler, return $entry(function(e) { var deltaX = e.deltaX ? e.deltaX : -0.5*e.wheelDeltaX; var deltaY = e.deltaY ? e.deltaY : -0.5*e.wheelDeltaY; - + // IE8 has only delta y if (isNaN(deltaY)) { deltaY = -0.5*e.wheelDelta; } - + @com.vaadin.client.ui.VComboBox.JsniUtil::moveScrollFromEvent(*)(widget, deltaX, deltaY, e, e.deltaMode); }); }-*/; diff --git a/client/src/main/java/com/vaadin/client/ui/VCustomLayout.java b/client/src/main/java/com/vaadin/client/ui/VCustomLayout.java index fa42637b55..374c241409 100644 --- a/client/src/main/java/com/vaadin/client/ui/VCustomLayout.java +++ b/client/src/main/java/com/vaadin/client/ui/VCustomLayout.java @@ -305,10 +305,12 @@ public class VCustomLayout extends ComplexPanel { */ public void updateCaption(ComponentConnector childConnector) { Widget widget = childConnector.getWidget(); - if (widget.getParent() != this) { + + if (!widget.isAttached()) { // Widget has not been added because the location was not found return; } + VCaptionWrapper wrapper = childWidgetToCaptionWrapper.get(widget); if (VCaption.isNeeded(childConnector)) { if (wrapper == null) { diff --git a/client/src/main/java/com/vaadin/client/ui/VDragAndDropWrapper.java b/client/src/main/java/com/vaadin/client/ui/VDragAndDropWrapper.java index 2a07cf8744..9f53935440 100644 --- a/client/src/main/java/com/vaadin/client/ui/VDragAndDropWrapper.java +++ b/client/src/main/java/com/vaadin/client/ui/VDragAndDropWrapper.java @@ -392,6 +392,7 @@ public class VDragAndDropWrapper extends VCustomComponent public boolean html5DragDrop(VHtml5DragEvent event) { if (dropHandler == null || !currentlyValid) { + VDragAndDropManager.get().interruptDrag(); return true; } try { @@ -466,11 +467,11 @@ public class VDragAndDropWrapper extends VCustomComponent public final native void postFile(VHtml5File file) /*-{ - + this.setRequestHeader('Content-Type', 'multipart/form-data'); // Seems like IE10 will loose the file if we don't keep a reference to it... this.fileBeingUploaded = file; - + this.send(file); }-*/; @@ -626,19 +627,19 @@ public class VDragAndDropWrapper extends VCustomComponent protected native void hookHtml5Events(com.google.gwt.user.client.Element el) /*-{ var me = this; - + el.addEventListener("dragenter", $entry(function(ev) { return me.@com.vaadin.client.ui.VDragAndDropWrapper::html5DragEnter(Lcom/vaadin/client/ui/dd/VHtml5DragEvent;)(ev); }), false); - + el.addEventListener("dragleave", $entry(function(ev) { return me.@com.vaadin.client.ui.VDragAndDropWrapper::html5DragLeave(Lcom/vaadin/client/ui/dd/VHtml5DragEvent;)(ev); }), false); - + el.addEventListener("dragover", $entry(function(ev) { return me.@com.vaadin.client.ui.VDragAndDropWrapper::html5DragOver(Lcom/vaadin/client/ui/dd/VHtml5DragEvent;)(ev); }), false); - + el.addEventListener("drop", $entry(function(ev) { return me.@com.vaadin.client.ui.VDragAndDropWrapper::html5DragDrop(Lcom/vaadin/client/ui/dd/VHtml5DragEvent;)(ev); }), false); diff --git a/client/src/main/java/com/vaadin/client/ui/VWindow.java b/client/src/main/java/com/vaadin/client/ui/VWindow.java index 98fdcc3707..caf41785a7 100644 --- a/client/src/main/java/com/vaadin/client/ui/VWindow.java +++ b/client/src/main/java/com/vaadin/client/ui/VWindow.java @@ -691,6 +691,8 @@ public class VWindow extends VOverlay implements ShortcutActionHandlerOwner, public void hide() { if (vaadinModality) { hideModalityCurtain(); + hideDraggingCurtain(); + hideResizingCurtain(); } super.hide(); diff --git a/client/src/main/java/com/vaadin/client/widget/grid/EditorHandler.java b/client/src/main/java/com/vaadin/client/widget/grid/EditorHandler.java index 6c23d8af87..14467987cf 100644 --- a/client/src/main/java/com/vaadin/client/widget/grid/EditorHandler.java +++ b/client/src/main/java/com/vaadin/client/widget/grid/EditorHandler.java @@ -55,9 +55,9 @@ public interface EditorHandler<T> { public int getRowIndex(); /** - * Returns the index of the column being focused. + * Returns the DOM index of the column being focused. * - * @return the column index + * @return the column index (excluding hidden columns) */ public int getColumnIndex(); diff --git a/client/src/main/java/com/vaadin/client/widget/grid/GridEventHandler.java b/client/src/main/java/com/vaadin/client/widget/grid/GridEventHandler.java index cc3ccc6c83..d5e2e27496 100644 --- a/client/src/main/java/com/vaadin/client/widget/grid/GridEventHandler.java +++ b/client/src/main/java/com/vaadin/client/widget/grid/GridEventHandler.java @@ -31,4 +31,4 @@ public interface GridEventHandler<T> { * the event that occurred */ public void onEvent(GridEvent<T> event); -}
\ No newline at end of file +} diff --git a/client/src/main/java/com/vaadin/client/widgets/Grid.java b/client/src/main/java/com/vaadin/client/widgets/Grid.java index a135827a5a..a58418d443 100755 --- a/client/src/main/java/com/vaadin/client/widgets/Grid.java +++ b/client/src/main/java/com/vaadin/client/widgets/Grid.java @@ -1097,15 +1097,15 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, private Grid<T> grid; private final int rowIndex; - private final int columnIndex; + private final int columnIndexDOM; private RequestCallback<T> callback; private boolean completed = false; - public EditorRequestImpl(Grid<T> grid, int rowIndex, int columnIndex, + public EditorRequestImpl(Grid<T> grid, int rowIndex, int columnIndexDOM, RequestCallback<T> callback) { this.grid = grid; this.rowIndex = rowIndex; - this.columnIndex = columnIndex; + this.columnIndexDOM = columnIndexDOM; this.callback = callback; } @@ -1116,7 +1116,7 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, @Override public int getColumnIndex() { - return columnIndex; + return columnIndexDOM; } @Override @@ -1285,13 +1285,13 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, } /** - * Returns the column index the editor was opened at. If the editor is - * not open, returns -1. + * Returns the DOM column index (excluding hidden columns) the editor + * was opened at. If the editor is not open, returns -1. * * @return the column index or -1 if editor is not open */ public int getFocusedColumnIndex() { - return getEditor().focusedColumnIndex; + return getEditor().focusedColumnIndexDOM; } } @@ -1362,7 +1362,7 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, private boolean enabled = false; private State state = State.INACTIVE; private int rowIndex = -1; - private int focusedColumnIndex = -1; + private int focusedColumnIndexDOM = -1; private String styleName = null; private HandlerRegistration hScrollHandler; @@ -1427,10 +1427,10 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, bindTimeout.cancel(); rowIndex = request.getRowIndex(); - focusedColumnIndex = request.getColumnIndex(); - if (focusedColumnIndex >= 0) { + focusedColumnIndexDOM = request.getColumnIndex(); + if (focusedColumnIndexDOM >= 0) { // Update internal focus of Grid - grid.focusCell(rowIndex, focusedColumnIndex); + grid.focusCell(rowIndex, focusedColumnIndexDOM); } showOverlay(); @@ -1539,9 +1539,10 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, * * @param rowIndex * the index of the row to be edited - * @param columnIndex - * the column index of the editor widget that should be - * initially focused or -1 to not set focus + * @param columnIndexDOM + * the column index (excluding hidden columns) of the editor + * widget that should be initially focused or -1 to not set + * focus * * @throws IllegalStateException * if this editor is not enabled @@ -1551,7 +1552,7 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, * * @since 7.5 */ - public void editRow(final int rowIndex, final int columnIndex) { + public void editRow(final int rowIndex, final int columnIndexDOM) { if (!enabled) { throw new IllegalStateException( "Cannot edit row: editor is not enabled"); @@ -1576,35 +1577,35 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, return; } } - if (columnIndex >= grid.getVisibleColumns().size()) { + if (columnIndexDOM >= grid.getVisibleColumns().size()) { throw new IllegalArgumentException( - "Edited column index " + columnIndex + "Edited column index " + columnIndexDOM + " was bigger than visible column count."); } if (this.rowIndex == rowIndex - && focusedColumnIndex == columnIndex) { + && focusedColumnIndexDOM == columnIndexDOM) { // NO-OP return; } if (this.rowIndex == rowIndex) { - if (focusedColumnIndex != columnIndex) { - if (columnIndex >= grid.getFrozenColumnCount()) { + if (focusedColumnIndexDOM != columnIndexDOM) { + if (columnIndexDOM >= grid.getFrozenColumnCount()) { // Scroll to new focused column. - grid.getEscalator().scrollToColumn(columnIndex, + grid.getEscalator().scrollToColumn(columnIndexDOM, ScrollDestination.ANY, 0); } - focusedColumnIndex = columnIndex; + focusedColumnIndexDOM = columnIndexDOM; } updateHorizontalScrollPosition(); // Update Grid internal focus and focus widget if possible - if (focusedColumnIndex >= 0) { - grid.focusCell(rowIndex, focusedColumnIndex); - focusColumn(focusedColumnIndex); + if (focusedColumnIndexDOM >= 0) { + grid.focusCell(rowIndex, focusedColumnIndexDOM); + focusColumn(focusedColumnIndexDOM); } // No need to request anything from the editor handler. @@ -1614,13 +1615,13 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, final Escalator escalator = grid.getEscalator(); if (escalator.getVisibleRowRange().contains(rowIndex)) { - show(rowIndex, columnIndex); + show(rowIndex, columnIndexDOM); } else { vScrollHandler = grid.addScrollHandler(new ScrollHandler() { @Override public void onScroll(ScrollEvent event) { if (escalator.getVisibleRowRange().contains(rowIndex)) { - show(rowIndex, columnIndex); + show(rowIndex, columnIndexDOM); vScrollHandler.removeHandler(); } } @@ -1653,7 +1654,7 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, "Cannot cancel edit: editor is not in edit mode"); } handler.cancel(new EditorRequestImpl<>(grid, rowIndex, - focusedColumnIndex, null), afterSave); + focusedColumnIndexDOM, null), afterSave); doCancel(); } @@ -1661,7 +1662,7 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, hideOverlay(); state = State.INACTIVE; rowIndex = -1; - focusedColumnIndex = -1; + focusedColumnIndexDOM = -1; grid.getEscalator().setScrollLocked(Direction.VERTICAL, false); updateSelectionCheckboxesAsNeeded(true); } @@ -1699,7 +1700,7 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, setButtonsEnabled(false); saveTimeout.schedule(SAVE_TIMEOUT_MS); EditorRequest<T> request = new EditorRequestImpl<>(grid, rowIndex, - focusedColumnIndex, saveRequestCallback); + focusedColumnIndexDOM, saveRequestCallback); handler.save(request); updateSelectionCheckboxesAsNeeded(true); } @@ -1871,8 +1872,8 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, grid.attachWidget(editor, cell); } - if (i == focusedColumnIndex) { - focusColumn(focusedColumnIndex); + if (i == focusedColumnIndexDOM) { + focusColumn(focusedColumnIndexDOM); } } else { cell.addClassName(NOT_EDITABLE_CLASS_NAME); @@ -1972,13 +1973,14 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, Unit.PX); } - private void focusColumn(int colIndex) { - if (colIndex < 0 || colIndex >= grid.getVisibleColumns().size()) { + private void focusColumn(int columnIndexDOM) { + if (columnIndexDOM < 0 + || columnIndexDOM >= grid.getVisibleColumns().size()) { // NO-OP return; } - Widget editor = getWidget(grid.getVisibleColumn(colIndex)); + Widget editor = getWidget(grid.getVisibleColumn(columnIndexDOM)); if (editor instanceof Focusable) { ((Focusable) editor).focus(); } else if (editor instanceof com.google.gwt.user.client.ui.Focusable) { @@ -2563,9 +2565,7 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, ++i; } while (cell != null); } - int columnIndex = getColumns() - .indexOf(getVisibleColumn(columnIndexDOM)); - if (columnIndex >= escalator.getColumnConfiguration() + if (columnIndexDOM >= escalator.getColumnConfiguration() .getFrozenColumnCount()) { escalator.scrollToColumn(columnIndexDOM, ScrollDestination.ANY, 10); @@ -6278,21 +6278,22 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, * * @param rowIndex * index of row to focus - * @param columnIndex - * index of cell to focus + * @param columnIndexDOM + * index (excluding hidden columns) of cell to focus */ - void focusCell(int rowIndex, int columnIndex) { + void focusCell(int rowIndex, int columnIndexDOM) { final Range rowRange = Range.between(0, dataSource.size()); final Range columnRange = Range.between(0, getVisibleColumns().size()); assert rowRange.contains( rowIndex) : "Illegal row index. Should be in range " + rowRange; assert columnRange.contains( - columnIndex) : "Illegal column index. Should be in range " + columnIndexDOM) : "Illegal column index. Should be in range " + columnRange; - if (rowRange.contains(rowIndex) && columnRange.contains(columnIndex)) { - cellFocusHandler.setCellFocus(rowIndex, columnIndex, + if (rowRange.contains(rowIndex) + && columnRange.contains(columnIndexDOM)) { + cellFocusHandler.setCellFocus(rowIndex, columnIndexDOM, escalator.getBody()); WidgetUtil.focus(getElement()); } @@ -7447,10 +7448,11 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, } Widget widget; - if (editor.focusedColumnIndex < 0) { + if (editor.focusedColumnIndexDOM < 0) { widget = null; } else { - widget = editor.getWidget(getColumn(editor.focusedColumnIndex)); + widget = editor + .getWidget(getColumn(editor.focusedColumnIndexDOM)); } EditorDomEvent<T> editorEvent = new EditorDomEvent<>( @@ -7556,8 +7558,7 @@ public class Grid<T> extends ResizeComposite implements HasSelectionHandlers<T>, if (!event.getCell().isHeader()) { return; } - if (event.getCell().getColumnIndex() < escalator - .getColumnConfiguration().getFrozenColumnCount()) { + if (event.getCell().getColumnIndex() < getFrozenColumnCount()) { return; } diff --git a/compatibility-server/src/test/java/com/vaadin/v7/tests/server/component/grid/MultiSelectionModelTest.java b/compatibility-server/src/test/java/com/vaadin/v7/tests/server/component/grid/MultiSelectionModelTest.java index b4ccb094d0..7840b1f246 100644 --- a/compatibility-server/src/test/java/com/vaadin/v7/tests/server/component/grid/MultiSelectionModelTest.java +++ b/compatibility-server/src/test/java/com/vaadin/v7/tests/server/component/grid/MultiSelectionModelTest.java @@ -17,6 +17,7 @@ package com.vaadin.v7.tests.server.component.grid; import java.util.ArrayList; import java.util.Arrays; +import java.util.Collections; import java.util.List; import org.junit.After; @@ -32,6 +33,7 @@ import com.vaadin.v7.event.SelectionEvent.SelectionListener; import com.vaadin.v7.shared.ui.grid.selection.MultiSelectionModelServerRpc; import com.vaadin.v7.shared.ui.grid.selection.MultiSelectionModelState; import com.vaadin.v7.ui.Grid; +import com.vaadin.v7.ui.Grid.SelectionModel.HasUserSelectionAllowed; public class MultiSelectionModelTest { diff --git a/compatibility-server/src/test/java/com/vaadin/v7/tests/server/component/grid/SingleSelectionModelTest.java b/compatibility-server/src/test/java/com/vaadin/v7/tests/server/component/grid/SingleSelectionModelTest.java index ffb07b986b..91d537824c 100644 --- a/compatibility-server/src/test/java/com/vaadin/v7/tests/server/component/grid/SingleSelectionModelTest.java +++ b/compatibility-server/src/test/java/com/vaadin/v7/tests/server/component/grid/SingleSelectionModelTest.java @@ -28,6 +28,7 @@ import com.vaadin.v7.event.SelectionEvent.SelectionListener; import com.vaadin.v7.shared.ui.grid.selection.SingleSelectionModelServerRpc; import com.vaadin.v7.ui.Grid; import com.vaadin.v7.ui.Grid.SelectionMode; +import com.vaadin.v7.ui.Grid.SelectionModel.HasUserSelectionAllowed; import com.vaadin.v7.ui.Grid.SingleSelectionModel; public class SingleSelectionModelTest { diff --git a/server/src/main/java/com/vaadin/server/LocaleService.java b/server/src/main/java/com/vaadin/server/LocaleService.java index 4398864c90..416677e1b2 100644 --- a/server/src/main/java/com/vaadin/server/LocaleService.java +++ b/server/src/main/java/com/vaadin/server/LocaleService.java @@ -158,56 +158,31 @@ public class LocaleService implements Serializable { /* * Date formatting (MM/DD/YYYY etc.) */ - - DateFormat dateFormat = DateFormat.getDateTimeInstance(DateFormat.SHORT, - DateFormat.SHORT, locale); + DateFormat dateFormat = DateFormat.getDateInstance(DateFormat.SHORT, + locale); + DateFormat timeFormat = DateFormat.getTimeInstance(DateFormat.SHORT, + locale); if (!(dateFormat instanceof SimpleDateFormat)) { getLogger().warning("Unable to get default date pattern for locale " + locale.toString()); dateFormat = new SimpleDateFormat(); } - final String df = ((SimpleDateFormat) dateFormat).toPattern(); - - int timeStart = df.indexOf('H'); - if (timeStart < 0) { - timeStart = df.indexOf('h'); - } - final int ampm_first = df.indexOf('a'); - // E.g. in Korean locale AM/PM is before h:mm - // TODO should take that into consideration on client-side as well, - // now always h:mm a - if (ampm_first > 0 && ampm_first < timeStart) { - timeStart = ampm_first; - } - // Hebrew locale has time before the date - final boolean timeFirst = timeStart == 0; - String dateformat; - if (timeFirst) { - int dateStart = df.indexOf(' '); - if (ampm_first > dateStart) { - dateStart = df.indexOf(' ', ampm_first); - } - dateformat = df.substring(dateStart + 1); - } else { - dateformat = df.substring(0, timeStart - 1); + if (!(timeFormat instanceof SimpleDateFormat)) { + getLogger().warning("Unable to get default time pattern for locale " + + locale.toString()); + timeFormat = new SimpleDateFormat(); } + final String datePattern = ((SimpleDateFormat) dateFormat).toPattern(); + final String timePattern = ((SimpleDateFormat) timeFormat).toPattern(); - localeData.dateFormat = dateformat.trim(); + localeData.dateFormat = datePattern.trim(); - /* - * Time formatting (24 or 12 hour clock and AM/PM suffixes) - */ - final String timeformat = df.substring(timeStart, df.length()); - /* - * Doesn't return second or milliseconds. - * - * We use timeformat to determine 12/24-hour clock - */ - final boolean twelve_hour_clock = timeformat.contains("a"); + final boolean twelve_hour_clock = timePattern.indexOf("a") > -1; // TODO there are other possibilities as well, like 'h' in french // (ignore them, too complicated) - final String hour_min_delimiter = timeformat.contains(".") ? "." : ":"; - // outWriter.print("\"tf\":\"" + timeformat + "\","); + final String hour_min_delimiter = timePattern.indexOf(".") > -1 ? "." + : ":"; + localeData.twelveHourClock = twelve_hour_clock; localeData.hourMinuteDelimiter = hour_min_delimiter; if (twelve_hour_clock) { diff --git a/server/src/main/java/com/vaadin/ui/renderers/AbstractJavaScriptRenderer.java b/server/src/main/java/com/vaadin/ui/renderers/AbstractJavaScriptRenderer.java index fd195efcb7..3d6c656fc6 100644 --- a/server/src/main/java/com/vaadin/ui/renderers/AbstractJavaScriptRenderer.java +++ b/server/src/main/java/com/vaadin/ui/renderers/AbstractJavaScriptRenderer.java @@ -70,7 +70,7 @@ import elemental.json.JsonValue; * <li><code>init(cell)</code> - Prepares a cell for rendering. Corresponds to * {@link com.vaadin.client.renderers.ComplexRenderer#init(com.vaadin.client.widget.grid.RendererCellReference)} * .</li> - * <li><code>destory(cell)</code> - Allows the renderer to release resources + * <li><code>destroy(cell)</code> - Allows the renderer to release resources * allocate for a cell that will no longer be used. Corresponds to * {@link com.vaadin.client.renderers.ComplexRenderer#destroy(com.vaadin.client.widget.grid.RendererCellReference)} * .</li> diff --git a/server/src/test/java/com/vaadin/server/LocaleServiceTest.java b/server/src/test/java/com/vaadin/server/LocaleServiceTest.java new file mode 100644 index 0000000000..a93489194c --- /dev/null +++ b/server/src/test/java/com/vaadin/server/LocaleServiceTest.java @@ -0,0 +1,1026 @@ +package com.vaadin.server; + +import java.util.HashMap; +import java.util.HashSet; +import java.util.Locale; +import java.util.Map; +import java.util.Set; + +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; +import org.mockito.Mockito; + +import com.vaadin.shared.ui.ui.UIState.LocaleData; +import com.vaadin.shared.ui.ui.UIState.LocaleServiceState; +import com.vaadin.ui.UI; + +public class LocaleServiceTest { + + private static Set<String> JAVA8_SUPPORTED_LOCALES = new HashSet<String>(); + static { + // From + // http://www.oracle.com/technetwork/java/javase/java8locales-2095355.html + JAVA8_SUPPORTED_LOCALES.add("sq-AL"); + JAVA8_SUPPORTED_LOCALES.add("ar-DZ"); + JAVA8_SUPPORTED_LOCALES.add("ar-BH"); + JAVA8_SUPPORTED_LOCALES.add("ar-EG"); + JAVA8_SUPPORTED_LOCALES.add("ar-IQ"); + JAVA8_SUPPORTED_LOCALES.add("ar-JO"); + JAVA8_SUPPORTED_LOCALES.add("ar-KW"); + JAVA8_SUPPORTED_LOCALES.add("ar-LB"); + JAVA8_SUPPORTED_LOCALES.add("ar-LY"); + JAVA8_SUPPORTED_LOCALES.add("ar-MA"); + JAVA8_SUPPORTED_LOCALES.add("ar-OM"); + JAVA8_SUPPORTED_LOCALES.add("ar-QA"); + JAVA8_SUPPORTED_LOCALES.add("ar-SA"); + JAVA8_SUPPORTED_LOCALES.add("ar-SD"); + JAVA8_SUPPORTED_LOCALES.add("ar-SY"); + JAVA8_SUPPORTED_LOCALES.add("ar-TN"); + JAVA8_SUPPORTED_LOCALES.add("ar-AE"); + JAVA8_SUPPORTED_LOCALES.add("ar-YE"); + JAVA8_SUPPORTED_LOCALES.add("be-BY"); + JAVA8_SUPPORTED_LOCALES.add("bg-BG"); + JAVA8_SUPPORTED_LOCALES.add("ca-ES"); + JAVA8_SUPPORTED_LOCALES.add("zh-CN"); + JAVA8_SUPPORTED_LOCALES.add("zh-SG"); + JAVA8_SUPPORTED_LOCALES.add("zh-HK"); + JAVA8_SUPPORTED_LOCALES.add("zh-TW"); + JAVA8_SUPPORTED_LOCALES.add("hr-HR"); + JAVA8_SUPPORTED_LOCALES.add("cs-CZ"); + JAVA8_SUPPORTED_LOCALES.add("da-DK"); + JAVA8_SUPPORTED_LOCALES.add("nl-BE"); + JAVA8_SUPPORTED_LOCALES.add("nl-NL"); + JAVA8_SUPPORTED_LOCALES.add("en-AU"); + JAVA8_SUPPORTED_LOCALES.add("en-CA"); + JAVA8_SUPPORTED_LOCALES.add("en-IN"); + JAVA8_SUPPORTED_LOCALES.add("en-IE"); + JAVA8_SUPPORTED_LOCALES.add("en-MT"); + JAVA8_SUPPORTED_LOCALES.add("en-NZ"); + JAVA8_SUPPORTED_LOCALES.add("en-PH"); + JAVA8_SUPPORTED_LOCALES.add("en-SG"); + JAVA8_SUPPORTED_LOCALES.add("en-ZA"); + JAVA8_SUPPORTED_LOCALES.add("en-GB"); + JAVA8_SUPPORTED_LOCALES.add("en-US"); + JAVA8_SUPPORTED_LOCALES.add("et-EE"); + JAVA8_SUPPORTED_LOCALES.add("fi-FI"); + JAVA8_SUPPORTED_LOCALES.add("fr-BE"); + JAVA8_SUPPORTED_LOCALES.add("fr-CA"); + JAVA8_SUPPORTED_LOCALES.add("fr-FR"); + JAVA8_SUPPORTED_LOCALES.add("fr-LU"); + JAVA8_SUPPORTED_LOCALES.add("fr-CH"); + JAVA8_SUPPORTED_LOCALES.add("de-AT"); + JAVA8_SUPPORTED_LOCALES.add("de-DE"); + JAVA8_SUPPORTED_LOCALES.add("de-LU"); + JAVA8_SUPPORTED_LOCALES.add("de-CH"); + JAVA8_SUPPORTED_LOCALES.add("el-CY"); + JAVA8_SUPPORTED_LOCALES.add("el-GR"); + JAVA8_SUPPORTED_LOCALES.add("iw-IL"); + JAVA8_SUPPORTED_LOCALES.add("hi-IN"); + JAVA8_SUPPORTED_LOCALES.add("hu-HU"); + JAVA8_SUPPORTED_LOCALES.add("is-IS"); + JAVA8_SUPPORTED_LOCALES.add("in-ID"); + JAVA8_SUPPORTED_LOCALES.add("ga-IE"); + JAVA8_SUPPORTED_LOCALES.add("it-IT"); + JAVA8_SUPPORTED_LOCALES.add("it-CH"); + JAVA8_SUPPORTED_LOCALES.add("ja-JP"); + JAVA8_SUPPORTED_LOCALES.add("ja-JP-u-ca-japanese"); + JAVA8_SUPPORTED_LOCALES.add("ja-JP-x-lvariant-JP"); + JAVA8_SUPPORTED_LOCALES.add("ko-KR"); + JAVA8_SUPPORTED_LOCALES.add("lv-LV"); + JAVA8_SUPPORTED_LOCALES.add("lt-LT"); + JAVA8_SUPPORTED_LOCALES.add("mk-MK"); + JAVA8_SUPPORTED_LOCALES.add("ms-MY"); + JAVA8_SUPPORTED_LOCALES.add("mt-MT"); + JAVA8_SUPPORTED_LOCALES.add("no-NO"); + JAVA8_SUPPORTED_LOCALES.add("nb-NO"); + JAVA8_SUPPORTED_LOCALES.add("nn-NO"); + JAVA8_SUPPORTED_LOCALES.add("no-NO-x-lvariant-NY"); + JAVA8_SUPPORTED_LOCALES.add("pl-PL"); + JAVA8_SUPPORTED_LOCALES.add("pt-BR"); + JAVA8_SUPPORTED_LOCALES.add("pt-PT"); + JAVA8_SUPPORTED_LOCALES.add("ro-RO"); + JAVA8_SUPPORTED_LOCALES.add("ru-RU"); + JAVA8_SUPPORTED_LOCALES.add("sr-BA"); + JAVA8_SUPPORTED_LOCALES.add("sr-ME"); + JAVA8_SUPPORTED_LOCALES.add("sr-RS"); + JAVA8_SUPPORTED_LOCALES.add("sr-Latn-BA"); + JAVA8_SUPPORTED_LOCALES.add("sr-Latn-ME"); + JAVA8_SUPPORTED_LOCALES.add("sr-Latn-RS"); + JAVA8_SUPPORTED_LOCALES.add("sk-SK"); + JAVA8_SUPPORTED_LOCALES.add("sl-SI"); + JAVA8_SUPPORTED_LOCALES.add("es-AR"); + JAVA8_SUPPORTED_LOCALES.add("es-BO"); + JAVA8_SUPPORTED_LOCALES.add("es-CL"); + JAVA8_SUPPORTED_LOCALES.add("es-CO"); + JAVA8_SUPPORTED_LOCALES.add("es-CR"); + JAVA8_SUPPORTED_LOCALES.add("es-DO"); + JAVA8_SUPPORTED_LOCALES.add("es-EC"); + JAVA8_SUPPORTED_LOCALES.add("es-SV"); + JAVA8_SUPPORTED_LOCALES.add("es-GT"); + JAVA8_SUPPORTED_LOCALES.add("es-HN"); + JAVA8_SUPPORTED_LOCALES.add("es-MX"); + JAVA8_SUPPORTED_LOCALES.add("es-NI"); + JAVA8_SUPPORTED_LOCALES.add("es-PA"); + JAVA8_SUPPORTED_LOCALES.add("es-PY"); + JAVA8_SUPPORTED_LOCALES.add("es-PE"); + JAVA8_SUPPORTED_LOCALES.add("es-PR"); + JAVA8_SUPPORTED_LOCALES.add("es-ES"); + JAVA8_SUPPORTED_LOCALES.add("es-US"); + JAVA8_SUPPORTED_LOCALES.add("es-UY"); + JAVA8_SUPPORTED_LOCALES.add("es-VE"); + JAVA8_SUPPORTED_LOCALES.add("sv-SE"); + JAVA8_SUPPORTED_LOCALES.add("th-TH"); + JAVA8_SUPPORTED_LOCALES.add("th-TH-u-ca-buddhist"); + JAVA8_SUPPORTED_LOCALES.add("th-TH-u-ca-buddhist-nu-thai"); + JAVA8_SUPPORTED_LOCALES.add("th-TH-x-lvariant-TH"); + JAVA8_SUPPORTED_LOCALES.add("tr-TR"); + JAVA8_SUPPORTED_LOCALES.add("uk-UA"); + JAVA8_SUPPORTED_LOCALES.add("vi-VN"); + } + private static Map<Locale, LocaleData> expectedLocaleData = new HashMap<Locale, LocaleData>(); + + static { + + LocaleData en_IE = new LocaleData(); + en_IE.dateFormat = "dd/MM/yy"; + en_IE.twelveHourClock = false; + en_IE.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("en", "IE"), en_IE); + + LocaleData ar_KW = new LocaleData(); + ar_KW.dateFormat = "dd/MM/yy"; + ar_KW.twelveHourClock = true; + ar_KW.hourMinuteDelimiter = ":"; + ar_KW.am = "ص"; + ar_KW.pm = "م"; + expectedLocaleData.put(new Locale("ar", "KW"), ar_KW); + + LocaleData ms_MY = new LocaleData(); + ms_MY.dateFormat = "dd/MM/yyyy"; + ms_MY.twelveHourClock = false; + ms_MY.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("ms", "MY"), ms_MY); + + LocaleData en_IN = new LocaleData(); + en_IN.dateFormat = "d/M/yy"; + en_IN.twelveHourClock = true; + en_IN.hourMinuteDelimiter = ":"; + en_IN.am = "AM"; + en_IN.pm = "PM"; + expectedLocaleData.put(new Locale("en", "IN"), en_IN); + + LocaleData es_BO = new LocaleData(); + es_BO.dateFormat = "dd-MM-yy"; + es_BO.twelveHourClock = true; + es_BO.hourMinuteDelimiter = ":"; + es_BO.am = "AM"; + es_BO.pm = "PM"; + expectedLocaleData.put(new Locale("es", "BO"), es_BO); + + LocaleData ar_SY = new LocaleData(); + ar_SY.dateFormat = "dd/MM/yy"; + ar_SY.twelveHourClock = true; + ar_SY.hourMinuteDelimiter = ":"; + ar_SY.am = "ص"; + ar_SY.pm = "م"; + expectedLocaleData.put(new Locale("ar", "SY"), ar_SY); + + LocaleData en_ZA = new LocaleData(); + en_ZA.dateFormat = "yyyy/MM/dd"; + en_ZA.twelveHourClock = true; + en_ZA.hourMinuteDelimiter = ":"; + en_ZA.am = "AM"; + en_ZA.pm = "PM"; + expectedLocaleData.put(new Locale("en", "ZA"), en_ZA); + + LocaleData no_NO = new LocaleData(); + no_NO.dateFormat = "dd.MM.yy"; + no_NO.twelveHourClock = false; + no_NO.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("no", "NO"), no_NO); + + LocaleData sr_LATN_BA = new LocaleData(); + sr_LATN_BA.dateFormat = "d.M.yy."; + sr_LATN_BA.twelveHourClock = false; + sr_LATN_BA.hourMinuteDelimiter = "."; + expectedLocaleData.put(new Locale("sr", "LATN", "BA"), sr_LATN_BA); + + LocaleData el_GR = new LocaleData(); + el_GR.dateFormat = "d/M/yyyy"; + el_GR.twelveHourClock = true; + el_GR.hourMinuteDelimiter = ":"; + el_GR.am = "πμ"; + el_GR.pm = "μμ"; + expectedLocaleData.put(new Locale("el", "GR"), el_GR); + + LocaleData sr_LATN_RS = new LocaleData(); + sr_LATN_RS.dateFormat = "d.M.yy."; + sr_LATN_RS.twelveHourClock = false; + sr_LATN_RS.hourMinuteDelimiter = "."; + expectedLocaleData.put(new Locale("sr", "LATN", "RS"), sr_LATN_RS); + + LocaleData nl_NL = new LocaleData(); + nl_NL.dateFormat = "d-M-yy"; + nl_NL.twelveHourClock = false; + nl_NL.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("nl", "NL"), nl_NL); + + LocaleData ar_LB = new LocaleData(); + ar_LB.dateFormat = "dd/MM/yy"; + ar_LB.twelveHourClock = true; + ar_LB.hourMinuteDelimiter = ":"; + ar_LB.am = "ص"; + ar_LB.pm = "م"; + expectedLocaleData.put(new Locale("ar", "LB"), ar_LB); + + LocaleData en_AU = new LocaleData(); + en_AU.dateFormat = "d/MM/yy"; + en_AU.twelveHourClock = true; + en_AU.hourMinuteDelimiter = ":"; + en_AU.am = "AM"; + en_AU.pm = "PM"; + expectedLocaleData.put(new Locale("en", "AU"), en_AU); + + LocaleData mk_MK = new LocaleData(); + mk_MK.dateFormat = "d.M.yy"; + mk_MK.twelveHourClock = false; + mk_MK.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("mk", "MK"), mk_MK); + + LocaleData ar_TN = new LocaleData(); + ar_TN.dateFormat = "dd/MM/yy"; + ar_TN.twelveHourClock = true; + ar_TN.hourMinuteDelimiter = ":"; + ar_TN.am = "ص"; + ar_TN.pm = "م"; + expectedLocaleData.put(new Locale("ar", "TN"), ar_TN); + + LocaleData ar_LY = new LocaleData(); + ar_LY.dateFormat = "dd/MM/yy"; + ar_LY.twelveHourClock = true; + ar_LY.hourMinuteDelimiter = ":"; + ar_LY.am = "ص"; + ar_LY.pm = "م"; + expectedLocaleData.put(new Locale("ar", "LY"), ar_LY); + + LocaleData hu_HU = new LocaleData(); + hu_HU.dateFormat = "yyyy.MM.dd."; + hu_HU.twelveHourClock = false; + hu_HU.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("hu", "HU"), hu_HU); + + LocaleData es_SV = new LocaleData(); + es_SV.dateFormat = "MM-dd-yy"; + es_SV.twelveHourClock = true; + es_SV.hourMinuteDelimiter = ":"; + es_SV.am = "AM"; + es_SV.pm = "PM"; + expectedLocaleData.put(new Locale("es", "SV"), es_SV); + + LocaleData es_CR = new LocaleData(); + es_CR.dateFormat = "dd/MM/yy"; + es_CR.twelveHourClock = true; + es_CR.hourMinuteDelimiter = ":"; + es_CR.am = "AM"; + es_CR.pm = "PM"; + expectedLocaleData.put(new Locale("es", "CR"), es_CR); + + LocaleData es_CL = new LocaleData(); + es_CL.dateFormat = "dd-MM-yy"; + es_CL.twelveHourClock = false; + es_CL.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("es", "CL"), es_CL); + + LocaleData fr_CA = new LocaleData(); + fr_CA.dateFormat = "yy-MM-dd"; + fr_CA.twelveHourClock = false; + fr_CA.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("fr", "CA"), fr_CA); + + LocaleData es_CO = new LocaleData(); + es_CO.dateFormat = "d/MM/yy"; + es_CO.twelveHourClock = true; + es_CO.hourMinuteDelimiter = ":"; + es_CO.am = "AM"; + es_CO.pm = "PM"; + expectedLocaleData.put(new Locale("es", "CO"), es_CO); + + LocaleData pl_PL = new LocaleData(); + pl_PL.dateFormat = "dd.MM.yy"; + pl_PL.twelveHourClock = false; + pl_PL.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("pl", "PL"), pl_PL); + + LocaleData pt_PT = new LocaleData(); + pt_PT.dateFormat = "dd-MM-yyyy"; + pt_PT.twelveHourClock = false; + pt_PT.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("pt", "PT"), pt_PT); + + LocaleData ar_EG = new LocaleData(); + ar_EG.dateFormat = "dd/MM/yy"; + ar_EG.twelveHourClock = true; + ar_EG.hourMinuteDelimiter = ":"; + ar_EG.am = "ص"; + ar_EG.pm = "م"; + expectedLocaleData.put(new Locale("ar", "EG"), ar_EG); + + LocaleData fr_BE = new LocaleData(); + fr_BE.dateFormat = "d/MM/yy"; + fr_BE.twelveHourClock = false; + fr_BE.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("fr", "BE"), fr_BE); + + LocaleData ga_IE = new LocaleData(); + ga_IE.dateFormat = "dd/MM/yyyy"; + ga_IE.twelveHourClock = false; + ga_IE.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("ga", "IE"), ga_IE); + + LocaleData ar_DZ = new LocaleData(); + ar_DZ.dateFormat = "dd/MM/yy"; + ar_DZ.twelveHourClock = true; + ar_DZ.hourMinuteDelimiter = ":"; + ar_DZ.am = "ص"; + ar_DZ.pm = "م"; + expectedLocaleData.put(new Locale("ar", "DZ"), ar_DZ); + + LocaleData en_SG = new LocaleData(); + en_SG.dateFormat = "d/M/yy"; + en_SG.twelveHourClock = true; + en_SG.hourMinuteDelimiter = ":"; + en_SG.am = "AM"; + en_SG.pm = "PM"; + expectedLocaleData.put(new Locale("en", "SG"), en_SG); + + LocaleData in_ID = new LocaleData(); + in_ID.dateFormat = "dd/MM/yy"; + in_ID.twelveHourClock = false; + in_ID.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("in", "ID"), in_ID); + + LocaleData ar_MA = new LocaleData(); + ar_MA.dateFormat = "dd/MM/yy"; + ar_MA.twelveHourClock = true; + ar_MA.hourMinuteDelimiter = ":"; + ar_MA.am = "ص"; + ar_MA.pm = "م"; + expectedLocaleData.put(new Locale("ar", "MA"), ar_MA); + + LocaleData th_TH_u_ca_buddhist_nu_thai = new LocaleData(); + th_TH_u_ca_buddhist_nu_thai.dateFormat = "d/M/yyyy"; + th_TH_u_ca_buddhist_nu_thai.twelveHourClock = false; + th_TH_u_ca_buddhist_nu_thai.hourMinuteDelimiter = "."; + expectedLocaleData.put(new Locale("th", "TH", "u-ca-buddhist-nu-thai"), + th_TH_u_ca_buddhist_nu_thai); + + LocaleData nb_NO = new LocaleData(); + nb_NO.dateFormat = "dd.MM.yy"; + nb_NO.twelveHourClock = false; + nb_NO.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("nb", "NO"), nb_NO); + + LocaleData es_HN = new LocaleData(); + es_HN.dateFormat = "MM-dd-yy"; + es_HN.twelveHourClock = true; + es_HN.hourMinuteDelimiter = ":"; + es_HN.am = "AM"; + es_HN.pm = "PM"; + expectedLocaleData.put(new Locale("es", "HN"), es_HN); + + LocaleData hr_HR = new LocaleData(); + hr_HR.dateFormat = "dd.MM.yy."; + hr_HR.twelveHourClock = false; + hr_HR.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("hr", "HR"), hr_HR); + + LocaleData es_PR = new LocaleData(); + es_PR.dateFormat = "MM-dd-yy"; + es_PR.twelveHourClock = true; + es_PR.hourMinuteDelimiter = ":"; + es_PR.am = "AM"; + es_PR.pm = "PM"; + expectedLocaleData.put(new Locale("es", "PR"), es_PR); + + LocaleData es_PY = new LocaleData(); + es_PY.dateFormat = "dd/MM/yy"; + es_PY.twelveHourClock = true; + es_PY.hourMinuteDelimiter = ":"; + es_PY.am = "AM"; + es_PY.pm = "PM"; + expectedLocaleData.put(new Locale("es", "PY"), es_PY); + + LocaleData sr_ME = new LocaleData(); + sr_ME.dateFormat = "d.M.yy."; + sr_ME.twelveHourClock = false; + sr_ME.hourMinuteDelimiter = "."; + expectedLocaleData.put(new Locale("sr", "ME"), sr_ME); + + LocaleData de_AT = new LocaleData(); + de_AT.dateFormat = "dd.MM.yy"; + de_AT.twelveHourClock = false; + de_AT.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("de", "AT"), de_AT); + + LocaleData is_IS = new LocaleData(); + is_IS.dateFormat = "d.M.yyyy"; + is_IS.twelveHourClock = false; + is_IS.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("is", "IS"), is_IS); + + LocaleData bg_BG = new LocaleData(); + bg_BG.dateFormat = "dd.MM.yy"; + bg_BG.twelveHourClock = false; + bg_BG.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("bg", "BG"), bg_BG); + + LocaleData cs_CZ = new LocaleData(); + cs_CZ.dateFormat = "d.M.yy"; + cs_CZ.twelveHourClock = false; + cs_CZ.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("cs", "CZ"), cs_CZ); + + LocaleData en_PH = new LocaleData(); + en_PH.dateFormat = "M/d/yy"; + en_PH.twelveHourClock = true; + en_PH.hourMinuteDelimiter = ":"; + en_PH.am = "AM"; + en_PH.pm = "PM"; + expectedLocaleData.put(new Locale("en", "PH"), en_PH); + + LocaleData zh_TW = new LocaleData(); + zh_TW.dateFormat = "yyyy/M/d"; + zh_TW.twelveHourClock = true; + zh_TW.hourMinuteDelimiter = ":"; + zh_TW.am = "上午"; + zh_TW.pm = "下午"; + expectedLocaleData.put(new Locale("zh", "TW"), zh_TW); + + LocaleData ko_KR = new LocaleData(); + ko_KR.dateFormat = "yy. M. d"; + ko_KR.twelveHourClock = true; + ko_KR.hourMinuteDelimiter = ":"; + ko_KR.am = "오전"; + ko_KR.pm = "오후"; + expectedLocaleData.put(new Locale("ko", "KR"), ko_KR); + + LocaleData sk_SK = new LocaleData(); + sk_SK.dateFormat = "d.M.yyyy"; + sk_SK.twelveHourClock = false; + sk_SK.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("sk", "SK"), sk_SK); + + LocaleData sr_LATN_ME = new LocaleData(); + sr_LATN_ME.dateFormat = "d.M.yy."; + sr_LATN_ME.twelveHourClock = false; + sr_LATN_ME.hourMinuteDelimiter = "."; + expectedLocaleData.put(new Locale("sr", "LATN", "ME"), sr_LATN_ME); + + LocaleData ar_OM = new LocaleData(); + ar_OM.dateFormat = "dd/MM/yy"; + ar_OM.twelveHourClock = true; + ar_OM.hourMinuteDelimiter = ":"; + ar_OM.am = "ص"; + ar_OM.pm = "م"; + expectedLocaleData.put(new Locale("ar", "OM"), ar_OM); + + LocaleData ru_RU = new LocaleData(); + ru_RU.dateFormat = "dd.MM.yy"; + ru_RU.twelveHourClock = false; + ru_RU.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("ru", "RU"), ru_RU); + + LocaleData sq_AL = new LocaleData(); + sq_AL.dateFormat = "yy-MM-dd"; + sq_AL.twelveHourClock = true; + sq_AL.hourMinuteDelimiter = "."; + sq_AL.am = "PD"; + sq_AL.pm = "MD"; + expectedLocaleData.put(new Locale("sq", "AL"), sq_AL); + + LocaleData es_AR = new LocaleData(); + es_AR.dateFormat = "dd/MM/yy"; + es_AR.twelveHourClock = false; + es_AR.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("es", "AR"), es_AR); + + LocaleData sv_SE = new LocaleData(); + sv_SE.dateFormat = "yyyy-MM-dd"; + sv_SE.twelveHourClock = false; + sv_SE.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("sv", "SE"), sv_SE); + + LocaleData ja_JP_x_lvariant_JP = new LocaleData(); + ja_JP_x_lvariant_JP.dateFormat = "yy/MM/dd"; + ja_JP_x_lvariant_JP.twelveHourClock = false; + ja_JP_x_lvariant_JP.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("ja", "JP", "x-lvariant-JP"), + ja_JP_x_lvariant_JP); + + LocaleData da_DK = new LocaleData(); + da_DK.dateFormat = "dd-MM-yy"; + da_DK.twelveHourClock = false; + da_DK.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("da", "DK"), da_DK); + + LocaleData uk_UA = new LocaleData(); + uk_UA.dateFormat = "dd.MM.yy"; + uk_UA.twelveHourClock = false; + uk_UA.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("uk", "UA"), uk_UA); + + LocaleData th_TH_u_ca_buddhist = new LocaleData(); + th_TH_u_ca_buddhist.dateFormat = "d/M/yyyy"; + th_TH_u_ca_buddhist.twelveHourClock = false; + th_TH_u_ca_buddhist.hourMinuteDelimiter = "."; + expectedLocaleData.put(new Locale("th", "TH", "u-ca-buddhist"), + th_TH_u_ca_buddhist); + + LocaleData en_US = new LocaleData(); + en_US.dateFormat = "M/d/yy"; + en_US.twelveHourClock = true; + en_US.hourMinuteDelimiter = ":"; + en_US.am = "AM"; + en_US.pm = "PM"; + expectedLocaleData.put(new Locale("en", "US"), en_US); + + LocaleData lv_LV = new LocaleData(); + lv_LV.dateFormat = "yy.d.M"; + lv_LV.twelveHourClock = false; + lv_LV.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("lv", "LV"), lv_LV); + + LocaleData ja_JP_u_ca_japanese = new LocaleData(); + ja_JP_u_ca_japanese.dateFormat = "yy/MM/dd"; + ja_JP_u_ca_japanese.twelveHourClock = false; + ja_JP_u_ca_japanese.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("ja", "JP", "u-ca-japanese"), + ja_JP_u_ca_japanese); + + LocaleData en_MT = new LocaleData(); + en_MT.dateFormat = "dd/MM/yyyy"; + en_MT.twelveHourClock = false; + en_MT.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("en", "MT"), en_MT); + + LocaleData zh_CN = new LocaleData(); + zh_CN.dateFormat = "yy-M-d"; + zh_CN.twelveHourClock = true; + zh_CN.hourMinuteDelimiter = ":"; + zh_CN.am = "上午"; + zh_CN.pm = "下午"; + expectedLocaleData.put(new Locale("zh", "CN"), zh_CN); + + LocaleData nl_BE = new LocaleData(); + nl_BE.dateFormat = "d/MM/yy"; + nl_BE.twelveHourClock = false; + nl_BE.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("nl", "BE"), nl_BE); + + LocaleData hi_IN = new LocaleData(); + hi_IN.dateFormat = "d/M/yy"; + hi_IN.twelveHourClock = true; + hi_IN.hourMinuteDelimiter = ":"; + hi_IN.am = "पूर्वाह्न"; + hi_IN.pm = "अपराह्न"; + expectedLocaleData.put(new Locale("hi", "IN"), hi_IN); + + LocaleData el_CY = new LocaleData(); + el_CY.dateFormat = "dd/MM/yyyy"; + el_CY.twelveHourClock = true; + el_CY.hourMinuteDelimiter = ":"; + el_CY.am = "ΠΜ"; + el_CY.pm = "ΜΜ"; + expectedLocaleData.put(new Locale("el", "CY"), el_CY); + + LocaleData de_CH = new LocaleData(); + de_CH.dateFormat = "dd.MM.yy"; + de_CH.twelveHourClock = false; + de_CH.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("de", "CH"), de_CH); + + LocaleData ja_JP = new LocaleData(); + ja_JP.dateFormat = "yy/MM/dd"; + ja_JP.twelveHourClock = false; + ja_JP.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("ja", "JP"), ja_JP); + + LocaleData ar_YE = new LocaleData(); + ar_YE.dateFormat = "dd/MM/yy"; + ar_YE.twelveHourClock = true; + ar_YE.hourMinuteDelimiter = ":"; + ar_YE.am = "ص"; + ar_YE.pm = "م"; + expectedLocaleData.put(new Locale("ar", "YE"), ar_YE); + + LocaleData ar_QA = new LocaleData(); + ar_QA.dateFormat = "dd/MM/yy"; + ar_QA.twelveHourClock = true; + ar_QA.hourMinuteDelimiter = ":"; + ar_QA.am = "ص"; + ar_QA.pm = "م"; + expectedLocaleData.put(new Locale("ar", "QA"), ar_QA); + + LocaleData es_GT = new LocaleData(); + es_GT.dateFormat = "d/MM/yy"; + es_GT.twelveHourClock = true; + es_GT.hourMinuteDelimiter = ":"; + es_GT.am = "AM"; + es_GT.pm = "PM"; + expectedLocaleData.put(new Locale("es", "GT"), es_GT); + + LocaleData nn_NO = new LocaleData(); + nn_NO.dateFormat = "dd.MM.yy"; + nn_NO.twelveHourClock = false; + nn_NO.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("nn", "NO"), nn_NO); + + LocaleData es_PE = new LocaleData(); + es_PE.dateFormat = "dd/MM/yy"; + es_PE.twelveHourClock = true; + es_PE.hourMinuteDelimiter = ":"; + es_PE.am = "AM"; + es_PE.pm = "PM"; + expectedLocaleData.put(new Locale("es", "PE"), es_PE); + + LocaleData en_NZ = new LocaleData(); + en_NZ.dateFormat = "d/MM/yy"; + en_NZ.twelveHourClock = true; + en_NZ.hourMinuteDelimiter = ":"; + en_NZ.am = "AM"; + en_NZ.pm = "PM"; + expectedLocaleData.put(new Locale("en", "NZ"), en_NZ); + + LocaleData be_BY = new LocaleData(); + be_BY.dateFormat = "d.M.yy"; + be_BY.twelveHourClock = false; + be_BY.hourMinuteDelimiter = "."; + expectedLocaleData.put(new Locale("be", "BY"), be_BY); + + LocaleData zh_SG = new LocaleData(); + zh_SG.dateFormat = "dd/MM/yy"; + zh_SG.twelveHourClock = true; + zh_SG.hourMinuteDelimiter = ":"; + zh_SG.am = "上午"; + zh_SG.pm = "下午"; + expectedLocaleData.put(new Locale("zh", "SG"), zh_SG); + + LocaleData ro_RO = new LocaleData(); + ro_RO.dateFormat = "dd.MM.yyyy"; + ro_RO.twelveHourClock = false; + ro_RO.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("ro", "RO"), ro_RO); + + LocaleData es_PA = new LocaleData(); + es_PA.dateFormat = "MM/dd/yy"; + es_PA.twelveHourClock = true; + es_PA.hourMinuteDelimiter = ":"; + es_PA.am = "AM"; + es_PA.pm = "PM"; + expectedLocaleData.put(new Locale("es", "PA"), es_PA); + + LocaleData mt_MT = new LocaleData(); + mt_MT.dateFormat = "dd/MM/yyyy"; + mt_MT.twelveHourClock = false; + mt_MT.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("mt", "MT"), mt_MT); + + LocaleData et_EE = new LocaleData(); + et_EE.dateFormat = "d.MM.yy"; + et_EE.twelveHourClock = false; + et_EE.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("et", "EE"), et_EE); + + LocaleData it_CH = new LocaleData(); + it_CH.dateFormat = "dd.MM.yy"; + it_CH.twelveHourClock = false; + it_CH.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("it", "CH"), it_CH); + + LocaleData th_TH_x_lvariant_TH = new LocaleData(); + th_TH_x_lvariant_TH.dateFormat = "d/M/yyyy"; + th_TH_x_lvariant_TH.twelveHourClock = false; + th_TH_x_lvariant_TH.hourMinuteDelimiter = "."; + expectedLocaleData.put(new Locale("th", "TH", "x-lvariant-TH"), + th_TH_x_lvariant_TH); + + LocaleData tr_TR = new LocaleData(); + tr_TR.dateFormat = "dd.MM.yyyy"; + tr_TR.twelveHourClock = false; + tr_TR.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("tr", "TR"), tr_TR); + + LocaleData fr_FR = new LocaleData(); + fr_FR.dateFormat = "dd/MM/yy"; + fr_FR.twelveHourClock = false; + fr_FR.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("fr", "FR"), fr_FR); + + LocaleData vi_VN = new LocaleData(); + vi_VN.dateFormat = "dd/MM/yyyy"; + vi_VN.twelveHourClock = false; + vi_VN.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("vi", "VN"), vi_VN); + + LocaleData en_GB = new LocaleData(); + en_GB.dateFormat = "dd/MM/yy"; + en_GB.twelveHourClock = false; + en_GB.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("en", "GB"), en_GB); + + LocaleData fi_FI = new LocaleData(); + fi_FI.dateFormat = "d.M.yyyy"; + fi_FI.twelveHourClock = false; + fi_FI.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("fi", "FI"), fi_FI); + + LocaleData en_CA = new LocaleData(); + en_CA.dateFormat = "dd/MM/yy"; + en_CA.twelveHourClock = true; + en_CA.hourMinuteDelimiter = ":"; + en_CA.am = "AM"; + en_CA.pm = "PM"; + expectedLocaleData.put(new Locale("en", "CA"), en_CA); + + LocaleData lt_LT = new LocaleData(); + lt_LT.dateFormat = "yy.M.d"; + lt_LT.twelveHourClock = false; + lt_LT.hourMinuteDelimiter = "."; + expectedLocaleData.put(new Locale("lt", "LT"), lt_LT); + + LocaleData ar_AE = new LocaleData(); + ar_AE.dateFormat = "dd/MM/yy"; + ar_AE.twelveHourClock = true; + ar_AE.hourMinuteDelimiter = ":"; + ar_AE.am = "ص"; + ar_AE.pm = "م"; + expectedLocaleData.put(new Locale("ar", "AE"), ar_AE); + + LocaleData sl_SI = new LocaleData(); + sl_SI.dateFormat = "d.M.y"; + sl_SI.twelveHourClock = false; + sl_SI.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("sl", "SI"), sl_SI); + + LocaleData es_DO = new LocaleData(); + es_DO.dateFormat = "dd/MM/yy"; + es_DO.twelveHourClock = true; + es_DO.hourMinuteDelimiter = ":"; + es_DO.am = "AM"; + es_DO.pm = "PM"; + expectedLocaleData.put(new Locale("es", "DO"), es_DO); + + LocaleData ar_IQ = new LocaleData(); + ar_IQ.dateFormat = "dd/MM/yy"; + ar_IQ.twelveHourClock = true; + ar_IQ.hourMinuteDelimiter = ":"; + ar_IQ.am = "ص"; + ar_IQ.pm = "م"; + expectedLocaleData.put(new Locale("ar", "IQ"), ar_IQ); + + LocaleData fr_CH = new LocaleData(); + fr_CH.dateFormat = "dd.MM.yy"; + fr_CH.twelveHourClock = false; + fr_CH.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("fr", "CH"), fr_CH); + + LocaleData es_EC = new LocaleData(); + es_EC.dateFormat = "dd/MM/yy"; + es_EC.twelveHourClock = false; + es_EC.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("es", "EC"), es_EC); + + LocaleData es_US = new LocaleData(); + es_US.dateFormat = "M/d/yy"; + es_US.twelveHourClock = true; + es_US.hourMinuteDelimiter = ":"; + es_US.am = "a.m."; + es_US.pm = "p.m."; + expectedLocaleData.put(new Locale("es", "US"), es_US); + + LocaleData iw_IL = new LocaleData(); + iw_IL.dateFormat = "dd/MM/yy"; + iw_IL.twelveHourClock = false; + iw_IL.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("iw", "IL"), iw_IL); + + LocaleData ar_SA = new LocaleData(); + ar_SA.dateFormat = "dd/MM/yy"; + ar_SA.twelveHourClock = true; + ar_SA.hourMinuteDelimiter = ":"; + ar_SA.am = "ص"; + ar_SA.pm = "م"; + expectedLocaleData.put(new Locale("ar", "SA"), ar_SA); + + LocaleData ca_ES = new LocaleData(); + ca_ES.dateFormat = "dd/MM/yy"; + ca_ES.twelveHourClock = false; + ca_ES.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("ca", "ES"), ca_ES); + + LocaleData de_DE = new LocaleData(); + de_DE.dateFormat = "dd.MM.yy"; + de_DE.twelveHourClock = false; + de_DE.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("de", "DE"), de_DE); + + LocaleData sr_BA = new LocaleData(); + sr_BA.dateFormat = "yy-MM-dd"; + sr_BA.twelveHourClock = false; + sr_BA.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("sr", "BA"), sr_BA); + + LocaleData zh_HK = new LocaleData(); + zh_HK.dateFormat = "yy'年'M'月'd'日'"; + zh_HK.twelveHourClock = true; + zh_HK.hourMinuteDelimiter = ":"; + zh_HK.am = "上午"; + zh_HK.pm = "下午"; + expectedLocaleData.put(new Locale("zh", "HK"), zh_HK); + + LocaleData ar_SD = new LocaleData(); + ar_SD.dateFormat = "dd/MM/yy"; + ar_SD.twelveHourClock = true; + ar_SD.hourMinuteDelimiter = ":"; + ar_SD.am = "ص"; + ar_SD.pm = "م"; + expectedLocaleData.put(new Locale("ar", "SD"), ar_SD); + + LocaleData pt_BR = new LocaleData(); + pt_BR.dateFormat = "dd/MM/yy"; + pt_BR.twelveHourClock = false; + pt_BR.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("pt", "BR"), pt_BR); + + LocaleData sr_RS = new LocaleData(); + sr_RS.dateFormat = "d.M.yy."; + sr_RS.twelveHourClock = false; + sr_RS.hourMinuteDelimiter = "."; + expectedLocaleData.put(new Locale("sr", "RS"), sr_RS); + + LocaleData es_UY = new LocaleData(); + es_UY.dateFormat = "dd/MM/yy"; + es_UY.twelveHourClock = true; + es_UY.hourMinuteDelimiter = ":"; + es_UY.am = "AM"; + es_UY.pm = "PM"; + expectedLocaleData.put(new Locale("es", "UY"), es_UY); + + LocaleData ar_BH = new LocaleData(); + ar_BH.dateFormat = "dd/MM/yy"; + ar_BH.twelveHourClock = true; + ar_BH.hourMinuteDelimiter = ":"; + ar_BH.am = "ص"; + ar_BH.pm = "م"; + expectedLocaleData.put(new Locale("ar", "BH"), ar_BH); + + LocaleData es_ES = new LocaleData(); + es_ES.dateFormat = "d/MM/yy"; + es_ES.twelveHourClock = false; + es_ES.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("es", "ES"), es_ES); + + LocaleData ar_JO = new LocaleData(); + ar_JO.dateFormat = "dd/MM/yy"; + ar_JO.twelveHourClock = true; + ar_JO.hourMinuteDelimiter = ":"; + ar_JO.am = "ص"; + ar_JO.pm = "م"; + expectedLocaleData.put(new Locale("ar", "JO"), ar_JO); + + LocaleData es_VE = new LocaleData(); + es_VE.dateFormat = "dd/MM/yy"; + es_VE.twelveHourClock = true; + es_VE.hourMinuteDelimiter = ":"; + es_VE.am = "AM"; + es_VE.pm = "PM"; + expectedLocaleData.put(new Locale("es", "VE"), es_VE); + + LocaleData es_MX = new LocaleData(); + es_MX.dateFormat = "d/MM/yy"; + es_MX.twelveHourClock = true; + es_MX.hourMinuteDelimiter = ":"; + es_MX.am = "AM"; + es_MX.pm = "PM"; + expectedLocaleData.put(new Locale("es", "MX"), es_MX); + + LocaleData it_IT = new LocaleData(); + it_IT.dateFormat = "dd/MM/yy"; + it_IT.twelveHourClock = false; + it_IT.hourMinuteDelimiter = "."; + expectedLocaleData.put(new Locale("it", "IT"), it_IT); + + LocaleData no_NO_x_lvariant_NY = new LocaleData(); + no_NO_x_lvariant_NY.dateFormat = "dd.MM.yy"; + no_NO_x_lvariant_NY.twelveHourClock = false; + no_NO_x_lvariant_NY.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("no", "NO", "x-lvariant-NY"), + no_NO_x_lvariant_NY); + + LocaleData de_LU = new LocaleData(); + de_LU.dateFormat = "dd.MM.yy"; + de_LU.twelveHourClock = false; + de_LU.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("de", "LU"), de_LU); + + LocaleData fr_LU = new LocaleData(); + fr_LU.dateFormat = "dd/MM/yy"; + fr_LU.twelveHourClock = false; + fr_LU.hourMinuteDelimiter = ":"; + expectedLocaleData.put(new Locale("fr", "LU"), fr_LU); + + LocaleData es_NI = new LocaleData(); + es_NI.dateFormat = "MM-dd-yy"; + es_NI.twelveHourClock = true; + es_NI.hourMinuteDelimiter = ":"; + es_NI.am = "AM"; + es_NI.pm = "PM"; + expectedLocaleData.put(new Locale("es", "NI"), es_NI); + + LocaleData th_TH = new LocaleData(); + th_TH.dateFormat = "d/M/yyyy"; + th_TH.twelveHourClock = false; + th_TH.hourMinuteDelimiter = "."; + expectedLocaleData.put(new Locale("th", "TH"), th_TH); + } + + private LocaleService localeService; + + @Before + public void setup() { + localeService = new LocaleService(Mockito.mock(UI.class), + new LocaleServiceState()); + } + + @Test + public void localeDateTimeFormat() { + for (Locale l : expectedLocaleData.keySet()) { + Assert.assertEquals("Error verifying locale " + l, + expectedLocaleData.get(l).dateFormat, + localeService.createLocaleData(l).dateFormat); + Assert.assertEquals("Error verifying locale " + l, + expectedLocaleData.get(l).twelveHourClock, + localeService.createLocaleData(l).twelveHourClock); + Assert.assertEquals("Error verifying locale " + l, + expectedLocaleData.get(l).am, + localeService.createLocaleData(l).am); + Assert.assertEquals("Error verifying locale " + l, + expectedLocaleData.get(l).pm, + localeService.createLocaleData(l).pm); + } + } + + public static void main(String[] args) { + for (String s : JAVA8_SUPPORTED_LOCALES) { + String[] parts = s.split("-", 3); + Locale l; + if (parts.length == 1) { + l = new Locale(parts[0]); + } else if (parts.length == 2) { + l = new Locale(parts[0], parts[1]); + } else if (parts.length == 3) { + l = new Locale(parts[0], parts[1], parts[2]); + } else { + throw new RuntimeException("Unexpected locale: " + s); + } + generateData(l); + } + } + + /** + * Helper method for generating the above data using LocaleService. + * + * @param locale + * the locale to generate data for + */ + private static void generateData(Locale locale) { + System.out.println(); + String id = locale.getLanguage(); + if (!locale.getCountry().equals("")) { + id += "_" + locale.getCountry(); + if (!locale.getVariant().equals("")) { + id += "_" + locale.getVariant(); + } + } + + String field = id.replace('-', '_'); + LocaleService localeService = new LocaleService(Mockito.mock(UI.class), + new LocaleServiceState()); + LocaleData localeData = localeService.createLocaleData(locale); + System.out.println("LocaleData " + field + " = new LocaleData();"); + System.out.println( + field + ".dateFormat = \"" + localeData.dateFormat + "\";"); + System.out.println(field + ".twelveHourClock = " + + localeData.twelveHourClock + ";"); + System.out.println(field + ".hourMinuteDelimiter = \"" + + localeData.hourMinuteDelimiter + "\";"); + if (localeData.twelveHourClock) { + System.out.println(field + ".am = \"" + localeData.am + "\";"); + System.out.println(field + ".pm = \"" + localeData.pm + "\";"); + } + System.out.println("expectedLocaleData.put(new Locale(\"" + + id.replaceAll("_", "\",\"") + "\"), " + field + ");"); + } + +}
\ No newline at end of file diff --git a/server/src/test/java/com/vaadin/ui/ComponentTest.java b/server/src/test/java/com/vaadin/ui/ComponentTest.java index 4907f945ac..1ea4867b93 100644 --- a/server/src/test/java/com/vaadin/ui/ComponentTest.java +++ b/server/src/test/java/com/vaadin/ui/ComponentTest.java @@ -15,12 +15,15 @@ */ package com.vaadin.ui; +import java.lang.reflect.Method; import java.util.Arrays; import java.util.HashSet; import org.junit.Assert; import com.vaadin.server.ClientConnector; +import com.vaadin.server.ServerRpcManager; +import com.vaadin.shared.communication.ServerRpc; import elemental.json.JsonObject; @@ -68,6 +71,29 @@ public class ComponentTest { } /** + * Gets the server rpc handler registered for a component. + * + * @param connector + * the connector which listens to the RPC + * @param serverRpcClass + * the server RPC class + * @return the server RPC handler + */ + public static <T extends ServerRpc> T getRpcProxy(ClientConnector connector, + Class<T> serverRpcClass) { + try { + ServerRpcManager<?> rpcManager = connector + .getRpcManager(serverRpcClass.getName()); + Method method = ServerRpcManager.class + .getDeclaredMethod("getImplementation"); + method.setAccessible(true); + return serverRpcClass.cast(method.invoke(rpcManager)); + } catch (ReflectiveOperationException e) { + throw new RuntimeException(e); + } + } + + /** * Asserts the set of properties that would be sent as state changes for the * given connector. * diff --git a/uitest/src/main/java/com/vaadin/tests/components/customlayout/CustomLayoutUpdateCaption.java b/uitest/src/main/java/com/vaadin/tests/components/customlayout/CustomLayoutUpdateCaption.java new file mode 100644 index 0000000000..6908ba1582 --- /dev/null +++ b/uitest/src/main/java/com/vaadin/tests/components/customlayout/CustomLayoutUpdateCaption.java @@ -0,0 +1,42 @@ +package com.vaadin.tests.components.customlayout; + +import com.vaadin.annotations.Widgetset; +import com.vaadin.server.VaadinRequest; +import com.vaadin.ui.Button; +import com.vaadin.ui.Button.ClickEvent; +import com.vaadin.ui.Button.ClickListener; +import com.vaadin.ui.CustomLayout; +import com.vaadin.ui.TextField; +import com.vaadin.ui.UI; +import com.vaadin.ui.VerticalLayout; + +@Widgetset("com.vaadin.DefaultWidgetSet") +public class CustomLayoutUpdateCaption extends UI { + @Override + protected void init(VaadinRequest vaadinRequest) { + CustomLayout content = new CustomLayout(); + content.setTemplateContents("<div>\n" + + " <div location=\"test1\"></div>\n" + + " <div location=\"test2\"></div>\n" + + " <div location=\"okbutton\"></div>\n" + "</div>"); + content.setSizeUndefined(); + setContent(content); + + Button loginButton = new Button("Test"); + final TextField username1 = new TextField(); + final TextField username2 = new TextField(); + username1.setCaption("initial"); + username2.setCaption("initial"); + content.addComponent(username1, "test1"); + content.addComponent(new VerticalLayout(username2), "test2"); + content.addComponent(loginButton, "okbutton"); + + loginButton.addClickListener(new ClickListener() { + @Override + public void buttonClick(ClickEvent e) { + username1.setCaption("updated"); + username2.setCaption("updated"); + } + }); + } +}
\ No newline at end of file diff --git a/uitest/src/main/java/com/vaadin/tests/components/draganddropwrapper/Html5DropDenied.java b/uitest/src/main/java/com/vaadin/tests/components/draganddropwrapper/Html5DropDenied.java new file mode 100644 index 0000000000..2f66033eed --- /dev/null +++ b/uitest/src/main/java/com/vaadin/tests/components/draganddropwrapper/Html5DropDenied.java @@ -0,0 +1,80 @@ +package com.vaadin.tests.components.draganddropwrapper; + +import com.vaadin.event.dd.DragAndDropEvent; +import com.vaadin.event.dd.DropHandler; +import com.vaadin.event.dd.acceptcriteria.AcceptAll; +import com.vaadin.event.dd.acceptcriteria.AcceptCriterion; +import com.vaadin.event.dd.acceptcriteria.ClientSideCriterion; +import com.vaadin.event.dd.acceptcriteria.Not; +import com.vaadin.server.ThemeResource; +import com.vaadin.server.VaadinRequest; +import com.vaadin.tests.components.AbstractTestUIWithLog; +import com.vaadin.ui.Button; +import com.vaadin.ui.Button.ClickEvent; +import com.vaadin.ui.DragAndDropWrapper; +import com.vaadin.ui.DragAndDropWrapper.DragStartMode; +import com.vaadin.ui.Image; + +public class Html5DropDenied extends AbstractTestUIWithLog { + + @Override + protected void setup(VaadinRequest request) { + Image sample = new Image(); + sample.setSource(new ThemeResource("../runo/icons/64/document.png")); + + Button neverButton = new Button("Never accepts drop"); + neverButton.setId("never"); + neverButton.addClickListener(new Button.ClickListener() { + @Override + public void buttonClick(ClickEvent event) { + log("click on " + event.getButton().getCaption()); + } + }); + + DragAndDropWrapper neverAccept = new DragAndDropWrapper(neverButton); + neverAccept.setSizeFull(); + neverAccept.setDragStartMode(DragStartMode.NONE); + neverAccept.setDropHandler(new DropHandler() { + + @Override + public AcceptCriterion getAcceptCriterion() { + return new Not((ClientSideCriterion) AcceptAll.get()); + } + + @Override + public void drop(DragAndDropEvent event) { + log("This should never happen"); + } + }); + Button alwaysButton = new Button("always accepts drop"); + alwaysButton.setId("always"); + alwaysButton.addClickListener(new Button.ClickListener() { + @Override + public void buttonClick(ClickEvent event) { + log("click on " + event.getButton().getCaption()); + } + }); + + DragAndDropWrapper alwaysAccept = new DragAndDropWrapper(alwaysButton); + alwaysAccept.setSizeFull(); + alwaysAccept.setDragStartMode(DragStartMode.NONE); + alwaysAccept.setDropHandler(new DropHandler() { + + @Override + public AcceptCriterion getAcceptCriterion() { + return AcceptAll.get(); + } + + @Override + public void drop(DragAndDropEvent event) { + log("Drop on always accept"); + } + }); + + addComponent(sample); + addComponent(neverAccept); + addComponent(alwaysAccept); + + } + +}
\ No newline at end of file diff --git a/uitest/src/main/java/com/vaadin/tests/components/grid/JavaScriptRenderers.java b/uitest/src/main/java/com/vaadin/tests/components/grid/JavaScriptRenderers.java index acf58c2217..16702dd831 100644 --- a/uitest/src/main/java/com/vaadin/tests/components/grid/JavaScriptRenderers.java +++ b/uitest/src/main/java/com/vaadin/tests/components/grid/JavaScriptRenderers.java @@ -18,10 +18,14 @@ package com.vaadin.tests.components.grid; import java.util.ArrayList; import java.util.List; +import com.vaadin.annotations.Widgetset; import com.vaadin.server.VaadinRequest; import com.vaadin.tests.components.AbstractReindeerTestUI; +import com.vaadin.ui.Button; import com.vaadin.ui.Grid; +import com.vaadin.ui.Label; +@Widgetset("com.vaadin.DefaultWidgetSet") public class JavaScriptRenderers extends AbstractReindeerTestUI { public static class ItemBean { @@ -81,6 +85,8 @@ public class JavaScriptRenderers extends AbstractReindeerTestUI { } } + private Grid<ItemBean> grid; + @Override protected void setup(VaadinRequest request) { List<ItemBean> items = new ArrayList<>(1000); @@ -92,6 +98,20 @@ public class JavaScriptRenderers extends AbstractReindeerTestUI { items.add(bean); } + Label clientLog = new Label(); + clientLog.setId("clientLog"); + addComponent(clientLog); + grid = createGrid(items); + addComponent(grid); + + addComponent(new Button("Recreate grid", e -> { + Grid<ItemBean> newGrid = createGrid(items); + replaceComponent(grid, newGrid); + grid = newGrid; + })); + } + + private Grid<ItemBean> createGrid(List<ItemBean> items) { Grid<ItemBean> grid = new Grid<>(); grid.addColumn(item -> item.getId().toString()).setCaption("Id"); @@ -99,10 +119,13 @@ public class JavaScriptRenderers extends AbstractReindeerTestUI { .setCaption("Bean"); grid.addColumn(ItemBean::getString, new JavaScriptStringRenderer()) .setCaption("String"); + grid.addColumn(ItemBean::getString, + new JavaScriptStringRendererWithDestoryMethod()) + .setCaption("String2"); grid.setItems(items); - addComponent(grid); + return grid; } } diff --git a/uitest/src/main/java/com/vaadin/tests/components/grid/JavaScriptStringRendererWithDestoryMethod.java b/uitest/src/main/java/com/vaadin/tests/components/grid/JavaScriptStringRendererWithDestoryMethod.java new file mode 100644 index 0000000000..266ff0736c --- /dev/null +++ b/uitest/src/main/java/com/vaadin/tests/components/grid/JavaScriptStringRendererWithDestoryMethod.java @@ -0,0 +1,15 @@ +package com.vaadin.tests.components.grid; + +import com.vaadin.annotations.JavaScript; +import com.vaadin.tests.components.grid.JavaScriptRenderers.ItemBean; +import com.vaadin.ui.renderers.AbstractJavaScriptRenderer; + +@JavaScript("JavaScriptStringRendererWithDestoryMethod.js") +public class JavaScriptStringRendererWithDestoryMethod + extends AbstractJavaScriptRenderer<ItemBean, String> { + + protected JavaScriptStringRendererWithDestoryMethod() { + super(String.class); + } + +}
\ No newline at end of file diff --git a/uitest/src/main/java/com/vaadin/tests/components/table/TableRemovedQuicklySendsInvalidRpcCalls.java b/uitest/src/main/java/com/vaadin/tests/components/table/TableRemovedQuicklySendsInvalidRpcCalls.java index 1252e4ce88..ae3667ff29 100644 --- a/uitest/src/main/java/com/vaadin/tests/components/table/TableRemovedQuicklySendsInvalidRpcCalls.java +++ b/uitest/src/main/java/com/vaadin/tests/components/table/TableRemovedQuicklySendsInvalidRpcCalls.java @@ -27,11 +27,7 @@ import com.vaadin.tests.components.AbstractReindeerTestUI; import com.vaadin.ui.Button; import com.vaadin.ui.Button.ClickEvent; import com.vaadin.ui.ConnectorTracker; -<<<<<<< HEAD import com.vaadin.v7.ui.Table; -======= -import com.vaadin.ui.Table; ->>>>>>> 62c0d73... Remove tracking of unregistered connectors (#8153) import elemental.json.JsonObject; diff --git a/uitest/src/main/resources/com/vaadin/tests/components/grid/JavaScriptStringRenderer.js b/uitest/src/main/resources/com/vaadin/tests/components/grid/JavaScriptStringRenderer.js index 475b453dcc..a309129136 100644 --- a/uitest/src/main/resources/com/vaadin/tests/components/grid/JavaScriptStringRenderer.js +++ b/uitest/src/main/resources/com/vaadin/tests/components/grid/JavaScriptStringRenderer.js @@ -2,4 +2,9 @@ com_vaadin_tests_components_grid_JavaScriptStringRenderer = function() { this.render = function(cell, data) { cell.element.textContent = data; } -}
\ No newline at end of file + + this.destroy = function(cell) { + document.getElementById("clientLog").innerHTML += "destroy: " + + cell.rowIndex + "/" + cell.columnIndex + "<br>"; + } +} diff --git a/uitest/src/main/resources/com/vaadin/tests/components/grid/JavaScriptStringRendererWithDestoryMethod.js b/uitest/src/main/resources/com/vaadin/tests/components/grid/JavaScriptStringRendererWithDestoryMethod.js new file mode 100644 index 0000000000..a75f2d5a63 --- /dev/null +++ b/uitest/src/main/resources/com/vaadin/tests/components/grid/JavaScriptStringRendererWithDestoryMethod.js @@ -0,0 +1,13 @@ +com_vaadin_tests_components_grid_JavaScriptStringRendererWithDestoryMethod = function() { + this.render = function(cell, data) { + cell.element.textContent = data; + // This one is for IE8 + cell.element.innerText = data; + } + + this.destory = function(cell) { + document.getElementById("clientLog").innerHTML += "destory: " + + cell.rowIndex + "/" + cell.columnIndex + "<br>"; + } + +} diff --git a/uitest/src/test/java/com/vaadin/tests/components/combobox/ComboBoxItemIconTest.java b/uitest/src/test/java/com/vaadin/tests/components/combobox/ComboBoxItemIconTest.java index ed6da0317a..7011a58179 100644 --- a/uitest/src/test/java/com/vaadin/tests/components/combobox/ComboBoxItemIconTest.java +++ b/uitest/src/test/java/com/vaadin/tests/components/combobox/ComboBoxItemIconTest.java @@ -1,7 +1,10 @@ package com.vaadin.tests.components.combobox; +import org.junit.Assert; import org.junit.Test; +import org.openqa.selenium.Keys; +import com.vaadin.testbench.By; import com.vaadin.testbench.elements.ComboBoxElement; import com.vaadin.tests.tb3.MultiBrowserTest; @@ -29,4 +32,41 @@ public class ComboBoxItemIconTest extends MultiBrowserTest { compareScreen("fi-au-selected"); } + @Test + public void iconResetOnSelectionCancelByEscape() { + openTestURL(); + ComboBoxElement cb = $(ComboBoxElement.class).get(1); + + assertSelection(cb, "hu.gif", "Hungary"); + cb.openPopup(); + cb.sendKeys(Keys.UP); + assertSelection(cb, "au.gif", "Australia"); + cb.sendKeys(Keys.ESCAPE); + assertSelection(cb, "hu.gif", "Hungary"); + } + + @Test + public void iconResetOnSelectionCancelByClickingOutside() { + openTestURL(); + ComboBoxElement cb = $(ComboBoxElement.class).get(1); + + assertSelection(cb, "hu.gif", "Hungary"); + cb.openPopup(); + cb.sendKeys(Keys.UP); + assertSelection(cb, "au.gif", "Australia"); + findElement(By.tagName("body")).click(); + assertSelection(cb, "hu.gif", "Hungary"); + + } + + private void assertSelection(ComboBoxElement cb, String imageSuffix, + String caption) { + Assert.assertEquals(caption, cb.getValue()); + String imgSrc = cb.findElement(By.className("v-icon")) + .getAttribute("src"); + imgSrc = imgSrc.substring(imgSrc.lastIndexOf('/') + 1); + Assert.assertEquals(imageSuffix, imgSrc); + + } + } diff --git a/uitest/src/test/java/com/vaadin/tests/components/customlayout/CustomLayoutUpdateCaptionTest.java b/uitest/src/test/java/com/vaadin/tests/components/customlayout/CustomLayoutUpdateCaptionTest.java new file mode 100644 index 0000000000..c74595d300 --- /dev/null +++ b/uitest/src/test/java/com/vaadin/tests/components/customlayout/CustomLayoutUpdateCaptionTest.java @@ -0,0 +1,30 @@ +package com.vaadin.tests.components.customlayout; + +import java.util.List; + +import org.junit.Assert; +import org.junit.Test; + +import com.vaadin.testbench.elements.ButtonElement; +import com.vaadin.testbench.elements.TextFieldElement; +import com.vaadin.tests.tb3.SingleBrowserTest; + +public class CustomLayoutUpdateCaptionTest extends SingleBrowserTest { + + @Test + public void captionUpdated() { + openTestURL(); + List<TextFieldElement> tfs = $(TextFieldElement.class).all(); + TextFieldElement tf1 = tfs.get(0); + TextFieldElement tf2 = tfs.get(1); + + Assert.assertEquals("initial", tf1.getCaption()); + Assert.assertEquals("initial", tf2.getCaption()); + + $(ButtonElement.class).first().click(); + + Assert.assertEquals("updated", tf1.getCaption()); + Assert.assertEquals("updated", tf2.getCaption()); + + } +}
\ No newline at end of file diff --git a/uitest/src/test/java/com/vaadin/tests/components/grid/GridSelectionTest.java b/uitest/src/test/java/com/vaadin/tests/components/grid/GridSelectionTest.java index 25a81984ea..45f7d54ebf 100644 --- a/uitest/src/test/java/com/vaadin/tests/components/grid/GridSelectionTest.java +++ b/uitest/src/test/java/com/vaadin/tests/components/grid/GridSelectionTest.java @@ -34,6 +34,11 @@ public class GridSelectionTest extends GridBasicsTest { assertTrue("row should become selected", getRow(0).isSelected()); toggleFirstRowSelection(); assertFalse("row shouldn't remain selected", getRow(0).isSelected()); + + toggleFirstRowSelection(); + assertTrue("row should become selected", getRow(0).isSelected()); + getGridElement().getCell(0, 0).click(); + assertFalse("row shouldn't remain selected", getRow(0).isSelected()); } @Test @@ -106,6 +111,11 @@ public class GridSelectionTest extends GridBasicsTest { assertTrue("First row was not selected.", getRow(0).isSelected()); assertTrue("Selection event was not correct", logContainsText( "SingleSelectionEvent: Selected: DataObject[0]")); + grid.getCell(0, 0).click(); + assertFalse("First row was not deselected.", getRow(0).isSelected()); + assertTrue("Deselection event was not correct", + logContainsText("SingleSelectionEvent: Selected: none")); + grid.getCell(5, 0).click(); assertTrue("Fifth row was not selected.", getRow(5).isSelected()); assertFalse("First row was still selected.", getRow(0).isSelected()); diff --git a/uitest/src/test/java/com/vaadin/tests/components/grid/JavaScriptRenderersTest.java b/uitest/src/test/java/com/vaadin/tests/components/grid/JavaScriptRenderersTest.java index 2cfb65d7ad..9b232cc459 100644 --- a/uitest/src/test/java/com/vaadin/tests/components/grid/JavaScriptRenderersTest.java +++ b/uitest/src/test/java/com/vaadin/tests/components/grid/JavaScriptRenderersTest.java @@ -17,7 +17,10 @@ package com.vaadin.tests.components.grid; import org.junit.Assert; import org.junit.Test; +import org.openqa.selenium.WebElement; +import com.vaadin.testbench.By; +import com.vaadin.testbench.elements.ButtonElement; import com.vaadin.testbench.elements.GridElement; import com.vaadin.testbench.elements.GridElement.GridCellElement; import com.vaadin.testbench.parallel.TestCategory; @@ -49,4 +52,20 @@ public class JavaScriptRenderersTest extends MultiBrowserTest { Assert.assertTrue( cell_1_1.getText().startsWith("Clicked 1 with key 2 at")); } + + @Test + public void testJavaScriptRendererDestroy() { + openTestURL("debug"); + waitForDebugMessage( + "Your JavaScript connector (com_vaadin_tests_components_grid_JavaScriptStringRendererWithDestoryMethod) has a typo. The destory method should be renamed to destroy."); + + $(ButtonElement.class).first().click(); + + WebElement log = findElement(By.id("clientLog")); + String text = log.getText(); + Assert.assertTrue(text.contains("destory: 19/3")); + Assert.assertTrue(text.contains("destroy: 19/2")); + Assert.assertTrue(text.contains("destroy: 0/2")); + Assert.assertTrue(text.contains("destory: 0/3")); + } } diff --git a/uitest/src/test/java/com/vaadin/tests/themes/valo/ModalWindowTest.java b/uitest/src/test/java/com/vaadin/tests/themes/valo/ModalWindowTest.java index 1d734ffd7a..79ad0ec471 100644 --- a/uitest/src/test/java/com/vaadin/tests/themes/valo/ModalWindowTest.java +++ b/uitest/src/test/java/com/vaadin/tests/themes/valo/ModalWindowTest.java @@ -1,10 +1,14 @@ package com.vaadin.tests.themes.valo; import static org.hamcrest.core.Is.is; +import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertThat; +import static org.junit.Assert.assertTrue; import org.junit.Test; +import org.openqa.selenium.Keys; import org.openqa.selenium.WebElement; +import org.openqa.selenium.interactions.Actions; import com.vaadin.testbench.By; import com.vaadin.testbench.elements.ButtonElement; @@ -31,7 +35,42 @@ public class ModalWindowTest extends SingleBrowserTest { is("none")); } + @Test + public void modal_curtains_close_correctly() { + openTestURL(); + + openModalWindow(); + new Actions(getDriver()).moveToElement(findHeaderElement()) + .clickAndHold().moveByOffset(1, 1).perform(); + assertTrue(isElementPresent(By.className("v-window-draggingCurtain"))); + new Actions(getDriver()).sendKeys(findHeaderElement(), Keys.ESCAPE) + .release().perform(); + verifyCurtainsNotPresent(); + + openModalWindow(); + new Actions(getDriver()).moveToElement(findResizingElement()) + .clickAndHold().moveByOffset(1, 1).perform(); + assertTrue(isElementPresent(By.className("v-window-resizingCurtain"))); + new Actions(getDriver()).sendKeys(findResizingElement(), Keys.ESCAPE) + .release().perform(); + verifyCurtainsNotPresent(); + } + private void openModalWindow() { $(ButtonElement.class).get(1).click(); } -} + + private WebElement findHeaderElement() { + return findElement(By.className("v-window-header")); + } + + private WebElement findResizingElement() { + return findElement(By.className("v-window-resizebox")); + } + + private void verifyCurtainsNotPresent() { + assertFalse(isElementPresent(By.className("v-window-modalitycurtain"))); + assertFalse(isElementPresent(By.className("v-window-draggingCurtain"))); + assertFalse(isElementPresent(By.className("v-window-resizingCurtain"))); + } +}
\ No newline at end of file diff --git a/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/GridBasicFeaturesTest.java b/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/GridBasicFeaturesTest.java index 04bb29c5c8..7c4a5962f2 100644 --- a/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/GridBasicFeaturesTest.java +++ b/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/GridBasicFeaturesTest.java @@ -251,4 +251,8 @@ public abstract class GridBasicFeaturesTest extends MultiBrowserTest { } return null; } + + protected void toggleColumnHidden(int column) { + selectMenuPath("Component", "Columns", "Column " + column, "Hidden"); + } } diff --git a/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/server/GridColumnReorderTest.java b/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/server/GridColumnReorderTest.java index feac52c0d3..aac48dc4d2 100644 --- a/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/server/GridColumnReorderTest.java +++ b/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/server/GridColumnReorderTest.java @@ -209,6 +209,29 @@ public class GridColumnReorderTest extends GridBasicFeaturesTest { } @Test + public void testColumnReorder_draggingFrozenColumnsContainingHiddenColumns_impossible() { + // given + openTestURL(); + selectMenuPath("Component", "Size", "Width", "900px"); + toggleColumnReordering(); + setFrozenColumns(4); + toggleColumnHidden(1); + toggleColumnHidden(2); + assertColumnHeaderOrder(0, 3, 4, 5); + + // when + // drag frozen column out between non-frozen columns + dragAndDropDefaultColumnHeader(1, 2, CellSide.RIGHT); + + // then + // everything should be as before + assertColumnHeaderOrder(0, 3, 4, 5); + assertTrue(getGridElement().getHeaderCell(0, 0).isFrozen()); + assertTrue(getGridElement().getHeaderCell(0, 1).isFrozen()); + assertFalse(getGridElement().getHeaderCell(0, 2).isFrozen()); + } + + @Test public void testColumnReorder_draggingColumnOnTopOfFrozenColumn_columnDroppedRightOfFrozenColumns() { // given openTestURL(); diff --git a/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/server/GridColumnResizeTest.java b/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/server/GridColumnResizeTest.java index fda42e7739..14738bfa57 100644 --- a/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/server/GridColumnResizeTest.java +++ b/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/server/GridColumnResizeTest.java @@ -153,13 +153,13 @@ public class GridColumnResizeTest extends GridBasicFeaturesTest { selectMenuPath("Component", "Columns", "Toggle all column hidden state"); // Hides although already hidden - selectMenuPath("Component", "Columns", "Column 0", "Hidden"); + toggleColumnHidden(0); // Shows - selectMenuPath("Component", "Columns", "Column 0", "Hidden"); + toggleColumnHidden(0); // Hides although already hidden - selectMenuPath("Component", "Columns", "Column 2", "Hidden"); + toggleColumnHidden(2); // Shows - selectMenuPath("Component", "Columns", "Column 2", "Hidden"); + toggleColumnHidden(2); GridCellElement cell = getGridElement().getCell(0, 1); dragResizeColumn(1, 0, -cell.getSize().getWidth()); assertGreaterOrEqual("Cell got too small.", cell.getSize().getWidth(), diff --git a/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/server/GridKeyboardNavigationTest.java b/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/server/GridKeyboardNavigationTest.java index 6878a36bd5..2c03964d81 100644 --- a/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/server/GridKeyboardNavigationTest.java +++ b/uitest/src/test/java/com/vaadin/v7/tests/components/grid/basicfeatures/server/GridKeyboardNavigationTest.java @@ -229,4 +229,17 @@ public class GridKeyboardNavigationTest extends GridBasicFeaturesTest { column == focusedColumn && Math.abs(row - focusedRow) <= rowTolerance); } + + @Test + public void testNavigateOverHiddenColumnToFrozenColumn() { + openTestURL(); + setFrozenColumns(3); + toggleColumnHidden(1); + getGridElement().getCell(0, 2).click(); + assertFocusedCell(0, 2); + new Actions(getDriver()).sendKeys(Keys.ARROW_LEFT).perform(); + assertFocusedCell(0, 1); + new Actions(getDriver()).sendKeys(Keys.ARROW_LEFT).perform(); + assertFocusedCell(0, 0); + } } |