]> source.dussan.org Git - vaadin-framework.git/commitdiff
Support string data in javascript renderers (#18209)
authorLeif Åstrand <leif@vaadin.com>
Tue, 9 Jun 2015 12:41:25 +0000 (15:41 +0300)
committerLeif Åstrand <leif@vaadin.com>
Mon, 7 Mar 2016 06:44:38 +0000 (06:44 +0000)
Change-Id: I2be48aa7a60920193a2f4bd9a413979cb9c48f34

client-compiler/src/com/vaadin/server/widgetsetutils/metadata/RendererVisitor.java
client/src/com/vaadin/client/connectors/JavaScriptRendererConnector.java
uitest/src/com/vaadin/tests/components/grid/JavaScriptRenderers.java
uitest/src/com/vaadin/tests/components/grid/JavaScriptRenderersTest.java
uitest/src/com/vaadin/tests/components/grid/JavaScriptStringRenderer.java [new file with mode: 0644]
uitest/src/com/vaadin/tests/components/grid/JavaScriptStringRenderer.js [new file with mode: 0644]

index 2e54d00aabf64e288f4ccbefa4ac46806466cd10..8b645aa492e26f6146171510110613c1117da932 100644 (file)
@@ -22,8 +22,11 @@ import com.google.gwt.core.ext.typeinfo.JClassType;
 import com.google.gwt.core.ext.typeinfo.JMethod;
 import com.google.gwt.core.ext.typeinfo.JParameterizedType;
 import com.google.gwt.core.ext.typeinfo.JType;
+import com.google.gwt.core.ext.typeinfo.NotFoundException;
 import com.vaadin.client.connectors.AbstractRendererConnector;
 
+import elemental.json.JsonValue;
+
 /**
  * Generates type data for renderer connectors.
  * <ul>
@@ -86,12 +89,33 @@ public class RendererVisitor extends TypeVisitor {
         JType presentationType = getPresentationType(type, logger);
         bundle.setPresentationType(type, presentationType);
 
-        bundle.setNeedsSerialize(presentationType);
+        if (!hasCustomDecodeMethod(type, logger)) {
+            bundle.setNeedsSerialize(presentationType);
+        }
 
         logger.log(Type.DEBUG, "Presentation type of " + type + " is "
                 + presentationType);
     }
 
+    private static boolean hasCustomDecodeMethod(JClassType type,
+            TreeLogger logger) throws UnableToCompleteException {
+        try {
+            JMethod decodeMethod = ConnectorBundle.findInheritedMethod(type,
+                    "decode",
+                    type.getOracle().getType(JsonValue.class.getName()));
+            if (decodeMethod == null) {
+                throw new NotFoundException();
+            }
+
+            return !decodeMethod.getEnclosingType().getQualifiedSourceName()
+                    .equals(AbstractRendererConnector.class.getName());
+        } catch (NotFoundException e) {
+            logger.log(Type.ERROR, "Can't find decode method for renderer "
+                    + type, e);
+            throw new UnableToCompleteException();
+        }
+    }
+
     private static JType getPresentationType(JClassType type, TreeLogger logger)
             throws UnableToCompleteException {
         JClassType originalType = type;
index 112623d1fe8c6a757c4b70fa15f40670c453477a..1229922a9c33f8012e2b41d63cc8a11721a00929 100644 (file)
@@ -42,9 +42,11 @@ import elemental.json.JsonValue;
  * @since 7.4
  * @author Vaadin Ltd
  */
+// This is really typed to <JsonValue>, but because of the way native strings
+// are not always instanceof JsonValue, we need to accept Object
 @Connect(AbstractJavaScriptRenderer.class)
 public class JavaScriptRendererConnector extends
-        AbstractRendererConnector<JsonValue> implements
+        AbstractRendererConnector<Object> implements
         HasJavaScriptConnectorHelper {
     private final JavaScriptConnectorHelper helper = new JavaScriptConnectorHelper(
             this);
@@ -131,7 +133,7 @@ public class JavaScriptRendererConnector extends
     }-*/;
 
     @Override
-    protected Renderer<JsonValue> createRenderer() {
+    protected Renderer<Object> createRenderer() {
         helper.ensureJavascriptInited();
 
         if (!hasFunction("render")) {
@@ -146,11 +148,13 @@ public class JavaScriptRendererConnector extends
         final boolean hasGetConsumedEvents = hasFunction("getConsumedEvents");
         final boolean hasOnBrowserEvent = hasFunction("onBrowserEvent");
 
-        return new ComplexRenderer<JsonValue>() {
+        return new ComplexRenderer<Object>() {
             @Override
-            public void render(RendererCellReference cell, JsonValue data) {
-                render(helper.getConnectorWrapper(), getJsCell(cell),
-                        Util.json2jso(data));
+            public void render(RendererCellReference cell, Object data) {
+                if (data instanceof JsonValue) {
+                    data = Util.json2jso((JsonValue) data);
+                }
+                render(helper.getConnectorWrapper(), getJsCell(cell), data);
             }
 
             private JavaScriptObject getJsCell(CellReference<?> cell) {
@@ -159,7 +163,7 @@ public class JavaScriptRendererConnector extends
             }
 
             public native void render(JavaScriptObject wrapper,
-                    JavaScriptObject cell, JavaScriptObject data)
+                    JavaScriptObject cell, Object data)
             /*-{
                 wrapper.render(cell, data);
             }-*/;
@@ -262,7 +266,7 @@ public class JavaScriptRendererConnector extends
     }
 
     @Override
-    public JsonValue decode(JsonValue value) {
+    public Object decode(JsonValue value) {
         // Let the js logic decode the raw json that the server sent
         return value;
     }
index 4bfa244c22773a83e458a5f90adcdc1a028e4fc1..8f888831616fb0e98c038586cc444540793895f5 100644 (file)
@@ -55,6 +55,7 @@ public class JavaScriptRenderers extends AbstractTestUI {
         IndexedContainer container = new IndexedContainer();
         container.addContainerProperty("id", Integer.class, Integer.valueOf(0));
         container.addContainerProperty("bean", MyBean.class, null);
+        container.addContainerProperty("string", String.class, "");
 
         for (int i = 0; i < 1000; i++) {
             Integer itemId = Integer.valueOf(i);
@@ -62,6 +63,7 @@ public class JavaScriptRenderers extends AbstractTestUI {
             item.getItemProperty("id").setValue(itemId);
             item.getItemProperty("bean").setValue(
                     new MyBean(i + 1, Integer.toString(i - 1)));
+            item.getItemProperty("string").setValue("string" + i);
         }
 
         Grid grid = new Grid(container);
@@ -69,6 +71,8 @@ public class JavaScriptRenderers extends AbstractTestUI {
         grid.getColumn("bean").setRenderer(new MyBeanJSRenderer());
         grid.getColumn("bean").setWidth(250);
 
+        grid.getColumn("string").setRenderer(new JavaScriptStringRenderer());
+
         addComponent(grid);
     }
 
index 2e86053ef3336ffd0a3a232431fbed7f56164bb9..917245188a6ea2bc701b7f6aa66b70a60ead27f9 100644 (file)
@@ -34,9 +34,13 @@ public class JavaScriptRenderersTest extends MultiBrowserTest {
         GridElement grid = $(GridElement.class).first();
         GridCellElement cell_1_1 = grid.getCell(1, 1);
 
+        GridCellElement cell_2_2 = grid.getCell(2, 2);
+
         // Verify render functionality
         Assert.assertEquals("Bean(2, 0)", cell_1_1.getText());
 
+        Assert.assertEquals("string2", cell_2_2.getText());
+
         // Verify init functionality
         Assert.assertEquals("1", cell_1_1.getAttribute("column"));
 
diff --git a/uitest/src/com/vaadin/tests/components/grid/JavaScriptStringRenderer.java b/uitest/src/com/vaadin/tests/components/grid/JavaScriptStringRenderer.java
new file mode 100644 (file)
index 0000000..ab3be6f
--- /dev/null
@@ -0,0 +1,29 @@
+/*
+ * Copyright 2000-2014 Vaadin Ltd.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.vaadin.tests.components.grid;
+
+import com.vaadin.annotations.JavaScript;
+import com.vaadin.ui.renderers.AbstractJavaScriptRenderer;
+
+@JavaScript("JavaScriptStringRenderer.js")
+public class JavaScriptStringRenderer extends
+        AbstractJavaScriptRenderer<String> {
+
+    protected JavaScriptStringRenderer() {
+        super(String.class);
+    }
+
+}
diff --git a/uitest/src/com/vaadin/tests/components/grid/JavaScriptStringRenderer.js b/uitest/src/com/vaadin/tests/components/grid/JavaScriptStringRenderer.js
new file mode 100644 (file)
index 0000000..475b453
--- /dev/null
@@ -0,0 +1,5 @@
+com_vaadin_tests_components_grid_JavaScriptStringRenderer = function() {
+       this.render = function(cell, data) {
+               cell.element.textContent = data;
+       }
+}
\ No newline at end of file