summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorArtur Signell <artur@vaadin.com>2016-01-24 15:30:15 +0200
committerTeemu Suo-Anttila <teemusa@vaadin.com>2016-04-11 09:12:57 +0000
commite4703b14fdfb312b8b6d71e78d1a7f13b5e2a933 (patch)
treef31583e02ee4a9680b3d700e54a961113ffac082
parent433dc8025ab7803fc25ef67e29fc67f7bb4d7d71 (diff)
downloadvaadin-framework-e4703b14fdfb312b8b6d71e78d1a7f13b5e2a933.tar.gz
vaadin-framework-e4703b14fdfb312b8b6d71e78d1a7f13b5e2a933.zip
Focus click element inside a drag'n'drop wrapper (#14826)
Focus inside a drag'n'drop wrapper does not work out of the box as mousedown is cancelled to avoid text selection when starting a dnd operation. This change explicitly calls focus on the element at the location which was clicked. Input elements will now be able to gain focus but e.g. clicking to move the caret inside a text area won't work as mousedown is cancelled. Change-Id: I89e046ddb0b1044bc6a2f11fda4edbe5fda25743
-rw-r--r--client/src/com/vaadin/client/ui/VDragAndDropWrapper.java20
-rw-r--r--uitest/src/com/vaadin/tests/components/draganddropwrapper/DragAndDropFocusObtain.java85
-rw-r--r--uitest/src/com/vaadin/tests/components/draganddropwrapper/DragAndDropFocusObtainTest.java26
3 files changed, 96 insertions, 35 deletions
diff --git a/client/src/com/vaadin/client/ui/VDragAndDropWrapper.java b/client/src/com/vaadin/client/ui/VDragAndDropWrapper.java
index d0584d150a..15ab9a6ce0 100644
--- a/client/src/com/vaadin/client/ui/VDragAndDropWrapper.java
+++ b/client/src/com/vaadin/client/ui/VDragAndDropWrapper.java
@@ -45,6 +45,7 @@ import com.vaadin.client.MouseEventDetailsBuilder;
import com.vaadin.client.Util;
import com.vaadin.client.VConsole;
import com.vaadin.client.ValueMap;
+import com.vaadin.client.WidgetUtil;
import com.vaadin.client.ui.dd.DDUtil;
import com.vaadin.client.ui.dd.VAbstractDropHandler;
import com.vaadin.client.ui.dd.VAcceptCallback;
@@ -106,25 +107,12 @@ public class VDragAndDropWrapper extends VCustomComponent implements
final int deltaX = Math.abs(event.getClientX() - startX);
final int deltaY = Math.abs(event.getClientY() - startY);
if ((deltaX + deltaY) < MIN_PX_DELTA) {
- setFocusOnLastElement(event);
+ Element clickedElement = WidgetUtil.getElementFromPoint(
+ event.getClientX(), event.getClientY());
+ clickedElement.focus();
}
}
- private void setFocusOnLastElement(final MouseUpEvent event) {
- Element el = event.getRelativeElement();
- getLastChildElement(el).focus();
- }
-
- private Element getLastChildElement(Element el) {
- do {
- if (el == null) {
- break;
- }
- el = el.getFirstChildElement();
- } while (el.getFirstChildElement() != null);
- return el;
- }
-
}, MouseUpEvent.getType());
addDomHandler(new TouchStartHandler() {
diff --git a/uitest/src/com/vaadin/tests/components/draganddropwrapper/DragAndDropFocusObtain.java b/uitest/src/com/vaadin/tests/components/draganddropwrapper/DragAndDropFocusObtain.java
index c182894db4..c7e16440bc 100644
--- a/uitest/src/com/vaadin/tests/components/draganddropwrapper/DragAndDropFocusObtain.java
+++ b/uitest/src/com/vaadin/tests/components/draganddropwrapper/DragAndDropFocusObtain.java
@@ -15,11 +15,22 @@
*/
package com.vaadin.tests.components.draganddropwrapper;
+import com.vaadin.data.Property.ValueChangeEvent;
+import com.vaadin.data.Property.ValueChangeListener;
+import com.vaadin.event.FieldEvents.FocusEvent;
+import com.vaadin.event.FieldEvents.FocusListener;
+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.server.VaadinRequest;
-import com.vaadin.tests.components.AbstractTestUI;
+import com.vaadin.tests.components.AbstractTestUIWithLog;
+import com.vaadin.ui.AbstractField;
import com.vaadin.ui.DragAndDropWrapper;
import com.vaadin.ui.DragAndDropWrapper.DragStartMode;
+import com.vaadin.ui.HorizontalLayout;
import com.vaadin.ui.TextArea;
+import com.vaadin.ui.TextField;
import com.vaadin.ui.VerticalLayout;
/**
@@ -29,18 +40,80 @@ import com.vaadin.ui.VerticalLayout;
* @since
* @author Vaadin Ltd
*/
-public class DragAndDropFocusObtain extends AbstractTestUI {
+public class DragAndDropFocusObtain extends AbstractTestUIWithLog {
+
+ private FocusListener focusListener = new FocusListener() {
+
+ @Override
+ public void focus(FocusEvent event) {
+ log("Field '" + event.getComponent().getCaption() + "' focused");
+
+ }
+ };
+ private ValueChangeListener listener = new ValueChangeListener() {
+
+ @Override
+ public void valueChange(ValueChangeEvent event) {
+ AbstractField f = (AbstractField) event.getProperty();
+ log("Value of " + f.getCaption() + " changed to " + f.getValue());
+ }
+ };
@Override
protected void setup(VaadinRequest request) {
+ HorizontalLayout hl = new HorizontalLayout();
+ VerticalLayout dndLayout = createLayout();
+ VerticalLayout normalLayout = createLayout();
+ DragAndDropWrapper wrapper = new DragAndDropWrapper(dndLayout);
+ wrapper.setDragStartMode(DragStartMode.COMPONENT);
+ wrapper.setDropHandler(new DropHandler() {
+
+ @Override
+ public AcceptCriterion getAcceptCriterion() {
+ return AcceptAll.get();
+ }
+
+ @Override
+ public void drop(DragAndDropEvent event) {
+ log("Dropped " + event.getTransferable().getSourceComponent()
+ + " on " + event.getTargetDetails().getTarget());
+
+ }
+ });
+ hl.addComponent(wrapper);
+ hl.addComponent(normalLayout);
+ addComponent(hl);
+
+ }
+
+ private VerticalLayout createLayout() {
VerticalLayout dndLayout = new VerticalLayout();
- TextArea area = new TextArea();
+
+ TextArea area = new TextArea("Text area 1");
area.setValue("text");
+ area.addValueChangeListener(listener);
+ area.addFocusListener(focusListener);
dndLayout.addComponent(area);
- DragAndDropWrapper wrapper = new DragAndDropWrapper(dndLayout);
- wrapper.setDragStartMode(DragStartMode.COMPONENT);
- addComponent(wrapper);
+ area = new TextArea("Text area 2");
+ area.setValue("text");
+ area.addValueChangeListener(listener);
+ area.addFocusListener(focusListener);
+ dndLayout.addComponent(area);
+
+ TextField field = new TextField("Text field 1");
+ field.setValue("text");
+ field.addValueChangeListener(listener);
+ field.addFocusListener(focusListener);
+ dndLayout.addComponent(field);
+
+ field = new TextField("Text field 2");
+ field.setValue("text");
+ field.addValueChangeListener(listener);
+ field.addFocusListener(focusListener);
+ dndLayout.addComponent(field);
+
+ return dndLayout;
}
@Override
diff --git a/uitest/src/com/vaadin/tests/components/draganddropwrapper/DragAndDropFocusObtainTest.java b/uitest/src/com/vaadin/tests/components/draganddropwrapper/DragAndDropFocusObtainTest.java
index ccb28b7103..7a2abe5efc 100644
--- a/uitest/src/com/vaadin/tests/components/draganddropwrapper/DragAndDropFocusObtainTest.java
+++ b/uitest/src/com/vaadin/tests/components/draganddropwrapper/DragAndDropFocusObtainTest.java
@@ -17,10 +17,8 @@ package com.vaadin.tests.components.draganddropwrapper;
import org.junit.Assert;
import org.junit.Test;
-import org.openqa.selenium.WebElement;
-import org.openqa.selenium.interactions.Actions;
-import com.vaadin.testbench.By;
+import com.vaadin.testbench.elements.AbstractTextFieldElement;
import com.vaadin.tests.tb3.MultiBrowserTest;
import com.vaadin.ui.DragAndDropWrapper;
@@ -36,16 +34,18 @@ public class DragAndDropFocusObtainTest extends MultiBrowserTest {
@Test
public void testTextAreaDndImage() {
openTestURL();
-
- WebElement wrapper = driver.findElement(By.className("v-ddwrapper"));
- Actions actions = new Actions(driver);
- actions.click(wrapper);
- actions.perform();
-
- WebElement focusedElement = driver.findElement(By
- .className("v-textarea-focus"));
- Assert.assertNotNull("Text area did not obtain focus after click",
- focusedElement);
+ int index = 1;
+ for (AbstractTextFieldElement ta : $(AbstractTextFieldElement.class)
+ .all()) {
+ String caption = ta.getCaption();
+ ta.click();
+ Assert.assertEquals(index + ". Field '" + caption + "' focused",
+ getLogRow(0));
+ index++;
+ }
+
+ // Make sure we checked all fields
+ Assert.assertEquals(8 + 1, index);
}