diff options
author | Adam Wagner <wbadam@users.noreply.github.com> | 2017-02-22 15:36:58 +0200 |
---|---|---|
committer | Pekka Hyvönen <pekka@vaadin.com> | 2017-02-22 15:36:58 +0200 |
commit | 813a99cfeff9d9cd70d77bd5d9ae75f5fa7b2ff5 (patch) | |
tree | de49df11876668ab0e0d4e6f42266bfdc5ff629d | |
parent | 998ea1f48a37ce04fea9ad4bcc49bf98ac511652 (diff) | |
download | vaadin-framework-813a99cfeff9d9cd70d77bd5d9ae75f5fa7b2ff5.tar.gz vaadin-framework-813a99cfeff9d9cd70d77bd5d9ae75f5fa7b2ff5.zip |
Make DragSource extension/component available in DropEvent (#8636)
* Make DragSource extension/component available in DropEvent (resolves #8439)
* Update drag and drop test to use new API
* Change type of drag source and update javadoc
* Use existing data map instead of DataTransfer
11 files changed, 87 insertions, 55 deletions
diff --git a/client/src/main/java/com/vaadin/client/extensions/DragSourceExtensionConnector.java b/client/src/main/java/com/vaadin/client/extensions/DragSourceExtensionConnector.java index 532b9877fc..b823167572 100644 --- a/client/src/main/java/com/vaadin/client/extensions/DragSourceExtensionConnector.java +++ b/client/src/main/java/com/vaadin/client/extensions/DragSourceExtensionConnector.java @@ -42,6 +42,11 @@ public class DragSourceExtensionConnector extends AbstractExtensionConnector { private static final String CLASS_DRAGGABLE = "v-draggable"; + /** + * Data type for storing drag source extension connector's ID + */ + static final String DATA_TYPE_DRAG_SOURCE_ID = "drag-source-id"; + // Create event listeners private final EventListener dragStartListener = this::onDragStart; private final EventListener dragEndListener = this::onDragEnd; @@ -104,6 +109,10 @@ public class DragSourceExtensionConnector extends AbstractExtensionConnector { nativeEvent.getDataTransfer().setData(format, data.get(format)); } + // Store the extension's connector ID in DataTransfer.data + nativeEvent.getDataTransfer() + .setData(DATA_TYPE_DRAG_SOURCE_ID, getConnectorId()); + // Initiate firing server side dragstart event when there is a // DragStartListener attached on the server side if (hasEventListener(DragSourceState.EVENT_DRAGSTART)) { diff --git a/client/src/main/java/com/vaadin/client/extensions/DropTargetExtensionConnector.java b/client/src/main/java/com/vaadin/client/extensions/DropTargetExtensionConnector.java index 3a9cbbfe84..37d62ad7c0 100644 --- a/client/src/main/java/com/vaadin/client/extensions/DropTargetExtensionConnector.java +++ b/client/src/main/java/com/vaadin/client/extensions/DropTargetExtensionConnector.java @@ -193,7 +193,8 @@ public class DropTargetExtensionConnector extends AbstractExtensionConnector { } getRpcProxy(DropTargetRpc.class) - .drop(types, data, getState().dropEffect); + .drop(types, data, getState().dropEffect, data.get( + DragSourceExtensionConnector.DATA_TYPE_DRAG_SOURCE_ID)); } removeTargetIndicator(getDropTargetElement()); diff --git a/server/src/main/java/com/vaadin/event/dnd/DragEndEvent.java b/server/src/main/java/com/vaadin/event/dnd/DragEndEvent.java index 47abea4eae..9de3611457 100644 --- a/server/src/main/java/com/vaadin/event/dnd/DragEndEvent.java +++ b/server/src/main/java/com/vaadin/event/dnd/DragEndEvent.java @@ -20,6 +20,7 @@ import java.util.List; import java.util.Map; import com.vaadin.shared.ui.dnd.EffectAllowed; +import com.vaadin.ui.AbstractComponent; import com.vaadin.ui.Component; /** @@ -29,7 +30,7 @@ import com.vaadin.ui.Component; * Type of the component that was dragged. * @see DragSourceExtension#addDragEndListener(DragEndListener) */ -public class DragEndEvent<T extends Component> extends Component.Event { +public class DragEndEvent<T extends AbstractComponent> extends Component.Event { private final Map<String, String> data; private final EffectAllowed effectAllowed; diff --git a/server/src/main/java/com/vaadin/event/dnd/DragEndListener.java b/server/src/main/java/com/vaadin/event/dnd/DragEndListener.java index 7b35bcab1d..51e113e4fd 100644 --- a/server/src/main/java/com/vaadin/event/dnd/DragEndListener.java +++ b/server/src/main/java/com/vaadin/event/dnd/DragEndListener.java @@ -18,7 +18,7 @@ package com.vaadin.event.dnd; import java.lang.reflect.Method; import com.vaadin.event.ConnectorEventListener; -import com.vaadin.ui.Component; +import com.vaadin.ui.AbstractComponent; /** * Interface to be implemented when creating a dragend listener on a drag @@ -29,7 +29,7 @@ import com.vaadin.ui.Component; * @see DragSourceExtension#addDragEndListener(DragEndListener) */ @FunctionalInterface -public interface DragEndListener<T extends Component> extends +public interface DragEndListener<T extends AbstractComponent> extends ConnectorEventListener { static final Method DRAGEND_METHOD = DragEndListener.class .getDeclaredMethods()[0]; diff --git a/server/src/main/java/com/vaadin/event/dnd/DragStartEvent.java b/server/src/main/java/com/vaadin/event/dnd/DragStartEvent.java index de6a1a79f4..8e9f82551c 100644 --- a/server/src/main/java/com/vaadin/event/dnd/DragStartEvent.java +++ b/server/src/main/java/com/vaadin/event/dnd/DragStartEvent.java @@ -20,6 +20,7 @@ import java.util.List; import java.util.Map; import com.vaadin.shared.ui.dnd.EffectAllowed; +import com.vaadin.ui.AbstractComponent; import com.vaadin.ui.Component; /** @@ -30,7 +31,7 @@ import com.vaadin.ui.Component; * Type of the component that is dragged. * @see DragSourceExtension#addDragStartListener(DragStartListener) */ -public class DragStartEvent<T extends Component> extends Component.Event { +public class DragStartEvent<T extends AbstractComponent> extends Component.Event { private final Map<String, String> data; private final EffectAllowed effectAllowed; diff --git a/server/src/main/java/com/vaadin/event/dnd/DragStartListener.java b/server/src/main/java/com/vaadin/event/dnd/DragStartListener.java index a9536144d9..d56254c58d 100644 --- a/server/src/main/java/com/vaadin/event/dnd/DragStartListener.java +++ b/server/src/main/java/com/vaadin/event/dnd/DragStartListener.java @@ -18,7 +18,7 @@ package com.vaadin.event.dnd; import java.lang.reflect.Method; import com.vaadin.event.ConnectorEventListener; -import com.vaadin.ui.Component; +import com.vaadin.ui.AbstractComponent; /** * Interface to be implemented when creating a dragstart listener on a drag @@ -29,7 +29,7 @@ import com.vaadin.ui.Component; * @see DragSourceExtension#addDragStartListener(DragStartListener) */ @FunctionalInterface -public interface DragStartListener<T extends Component> extends +public interface DragStartListener<T extends AbstractComponent> extends ConnectorEventListener { static final Method DRAGSTART_METHOD = DragStartListener.class .getDeclaredMethods()[0]; diff --git a/server/src/main/java/com/vaadin/event/dnd/DropEvent.java b/server/src/main/java/com/vaadin/event/dnd/DropEvent.java index 5257a06367..9a16efc097 100644 --- a/server/src/main/java/com/vaadin/event/dnd/DropEvent.java +++ b/server/src/main/java/com/vaadin/event/dnd/DropEvent.java @@ -18,8 +18,10 @@ package com.vaadin.event.dnd; import java.util.LinkedHashMap; import java.util.List; import java.util.Map; +import java.util.Optional; import com.vaadin.shared.ui.dnd.DropEffect; +import com.vaadin.ui.AbstractComponent; import com.vaadin.ui.Component; /** @@ -29,15 +31,17 @@ import com.vaadin.ui.Component; * Type of the drop target component. * @see DropTargetExtension#addDropListener(DropListener) */ -public class DropEvent<T extends Component> extends Component.Event { +public class DropEvent<T extends AbstractComponent> extends Component.Event { private final Map<String, String> data; private final DropEffect dropEffect; + private final DragSourceExtension<AbstractComponent> dragSourceExtension; + private final AbstractComponent dragSource; /** * Creates a server side drop event. * - * @param source - * Component that is dragged. + * @param target + * Component that received the drop. * @param types * List of data types from {@code DataTransfer.types} object. * @param data @@ -45,16 +49,24 @@ public class DropEvent<T extends Component> extends Component.Event { * DataTransfer} object. * @param dropEffect * Drop effect from {@code DataTransfer.dropEffect} object. + * @param dragSourceExtension + * Drag source extension of the component that initiated the drop + * event. */ - public DropEvent(T source, List<String> types, Map<String, String> data, - DropEffect dropEffect) { - super(source); + public DropEvent(T target, List<String> types, Map<String, String> data, + DropEffect dropEffect, + DragSourceExtension<AbstractComponent> dragSourceExtension) { + super(target); // Create a linked map that preserves the order of types this.data = new LinkedHashMap<>(); types.forEach(type -> this.data.put(type, data.get(type))); this.dropEffect = dropEffect; + + this.dragSourceExtension = dragSourceExtension; + this.dragSource = Optional.ofNullable(dragSourceExtension) + .map(DragSourceExtension::getParent).orElse(null); } /** @@ -79,6 +91,28 @@ public class DropEvent<T extends Component> extends Component.Event { } /** + * Returns the drag source component if the drag originated from a + * component in the same UI as the drop target component, or an empty + * optional. + * + * @return Drag source component or an empty optional. + */ + public Optional<AbstractComponent> getDragSourceComponent() { + return Optional.ofNullable(dragSource); + } + + /** + * Returns the extension of the drag source component if the drag + * originated from a component in the same UI as the drop target component, + * or an empty optional. + * + * @return Drag source extension or an empty optional + */ + public Optional<DragSourceExtension<AbstractComponent>> getDragSourceExtension() { + return Optional.ofNullable(dragSourceExtension); + } + + /** * Returns the drop target component where the drop event occurred. * * @return Component on which a drag source was dropped. diff --git a/server/src/main/java/com/vaadin/event/dnd/DropListener.java b/server/src/main/java/com/vaadin/event/dnd/DropListener.java index 41c1bfc6ff..98e8147fc3 100644 --- a/server/src/main/java/com/vaadin/event/dnd/DropListener.java +++ b/server/src/main/java/com/vaadin/event/dnd/DropListener.java @@ -18,7 +18,7 @@ package com.vaadin.event.dnd; import java.lang.reflect.Method; import com.vaadin.event.ConnectorEventListener; -import com.vaadin.ui.Component; +import com.vaadin.ui.AbstractComponent; /** * Interface to be implemented when creating a drop listener on a drop target @@ -29,7 +29,7 @@ import com.vaadin.ui.Component; * @see DropTargetExtension#addDropListener(DropListener) */ @FunctionalInterface -public interface DropListener<T extends Component> extends +public interface DropListener<T extends AbstractComponent> extends ConnectorEventListener { static final Method DROP_METHOD = DropListener.class .getDeclaredMethods()[0]; diff --git a/server/src/main/java/com/vaadin/event/dnd/DropTargetExtension.java b/server/src/main/java/com/vaadin/event/dnd/DropTargetExtension.java index e6f1fe1214..887361e883 100644 --- a/server/src/main/java/com/vaadin/event/dnd/DropTargetExtension.java +++ b/server/src/main/java/com/vaadin/event/dnd/DropTargetExtension.java @@ -18,6 +18,7 @@ package com.vaadin.event.dnd; import java.util.Objects; import com.vaadin.server.AbstractExtension; +import com.vaadin.server.ClientConnector; import com.vaadin.shared.Registration; import com.vaadin.shared.ui.dnd.DropEffect; import com.vaadin.shared.ui.dnd.DropTargetRpc; @@ -41,9 +42,17 @@ public class DropTargetExtension<T extends AbstractComponent> extends * Component to be extended. */ public DropTargetExtension(T target) { - registerRpc((DropTargetRpc) (types, data, dropEffect) -> { + registerRpc((DropTargetRpc) (types, data, dropEffect, dataSourceId) -> { + DragSourceExtension dragSource = null; + + ClientConnector connector = getUI().getConnectorTracker() + .getConnector(dataSourceId); + if (connector != null && connector instanceof DragSourceExtension) { + dragSource = (DragSourceExtension) connector; + } + DropEvent<T> event = new DropEvent<>(target, types, data, - dropEffect); + dropEffect, dragSource); fireEvent(event); }); diff --git a/shared/src/main/java/com/vaadin/shared/ui/dnd/DropTargetRpc.java b/shared/src/main/java/com/vaadin/shared/ui/dnd/DropTargetRpc.java index dd21278277..9f335f010d 100644 --- a/shared/src/main/java/com/vaadin/shared/ui/dnd/DropTargetRpc.java +++ b/shared/src/main/java/com/vaadin/shared/ui/dnd/DropTargetRpc.java @@ -36,7 +36,9 @@ public interface DropTargetRpc extends ServerRpc { * Contains data from {@code DataTransfer} object. * @param dropEffect * Drop effect set for the drop target where drop happened. + * @param dragSourceId + * Drag source component connector's ID. */ public void drop(List<String> types, Map<String, String> data, - DropEffect dropEffect); + DropEffect dropEffect, String dragSourceId); } diff --git a/uitest/src/main/java/com/vaadin/tests/dnd/DragAndDropCardShuffle.java b/uitest/src/main/java/com/vaadin/tests/dnd/DragAndDropCardShuffle.java index 8f5df032cc..745297cde8 100644 --- a/uitest/src/main/java/com/vaadin/tests/dnd/DragAndDropCardShuffle.java +++ b/uitest/src/main/java/com/vaadin/tests/dnd/DragAndDropCardShuffle.java @@ -15,23 +15,17 @@ */ package com.vaadin.tests.dnd; -import java.util.Optional; - import com.vaadin.event.dnd.DragSourceExtension; import com.vaadin.event.dnd.DropTargetExtension; -import com.vaadin.server.Extension; import com.vaadin.server.Page; import com.vaadin.server.VaadinRequest; +import com.vaadin.shared.ui.dnd.DropEffect; import com.vaadin.tests.components.AbstractTestUIWithLog; -import com.vaadin.ui.Component; import com.vaadin.ui.HorizontalLayout; import com.vaadin.ui.Label; public class DragAndDropCardShuffle extends AbstractTestUIWithLog { - // Data type for storing card position - private static final String DATA_INDEX = "index"; - // Create cards private final Label ace = new Label("A"); private final Label jack = new Label("J"); @@ -74,10 +68,6 @@ public class DragAndDropCardShuffle extends AbstractTestUIWithLog { DragSourceExtension<Label> dragSource = new DragSourceExtension<>( source); - // Set component position as transfer data - dragSource.setTransferData(DATA_INDEX, - String.valueOf(desk.getComponentIndex(source))); - // Add listeners dragSource.addDragStartListener(event -> { event.getComponent().addStyleName("dragged"); @@ -95,36 +85,21 @@ public class DragAndDropCardShuffle extends AbstractTestUIWithLog { DropTargetExtension<Label> dropTarget = new DropTargetExtension<>( target); + dropTarget.setDropEffect(DropEffect.MOVE); + // Add listener dropTarget.addDropListener(event -> { - // Retrieve the source's position - int sourceIndex = Integer - .valueOf(event.getTransferData(DATA_INDEX)); - - // Find source component - Component source = desk.getComponent(sourceIndex); - - // Swap source and target components - desk.replaceComponent(target, source); - - // Get DragSource extension for target component and set position data - Optional<Extension> targetExt = target.getExtensions().stream() - .filter(e -> e instanceof DragSourceExtension).findFirst(); - targetExt.ifPresent(extension -> { - ((DragSourceExtension) extension).setTransferData(DATA_INDEX, - String.valueOf(desk.getComponentIndex(target))); - }); + event.getDragSourceExtension().ifPresent(dragSource -> { + if (dragSource.getParent() instanceof Label) { + Label source = (Label) dragSource.getParent(); - // Get DragSource extension for source component and set position data - Optional<Extension> sourceExt = source.getExtensions().stream() - .filter(e -> e instanceof DragSourceExtension).findFirst(); - sourceExt.ifPresent(extension -> { - ((DragSourceExtension) extension).setTransferData(DATA_INDEX, - String.valueOf(desk.getComponentIndex(source))); - }); + // Swap source and target components + desk.replaceComponent(target, source); - log(((Label) source).getValue() + " dropped onto " + (event - .getComponent()).getValue()); + log(source.getValue() + " dropped onto " + event + .getComponent().getValue()); + } + }); }); } |