Skip to content

Commit

Permalink
Support string data in javascript renderers (#18209)
Browse files Browse the repository at this point in the history
Change-Id: I2be48aa7a60920193a2f4bd9a413979cb9c48f34
  • Loading branch information
Legioth committed Mar 7, 2016
1 parent a00fd32 commit 8f81ba9
Show file tree
Hide file tree
Showing 6 changed files with 79 additions and 9 deletions.
Expand Up @@ -22,8 +22,11 @@
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>
Expand Down Expand Up @@ -86,12 +89,33 @@ private void doPresentationType(TreeLogger logger, JClassType type,
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;
Expand Down
Expand Up @@ -42,9 +42,11 @@
* @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);
Expand Down Expand Up @@ -131,7 +133,7 @@ private static native boolean hasFunction(JavaScriptObject wrapper,
}-*/;

@Override
protected Renderer<JsonValue> createRenderer() {
protected Renderer<Object> createRenderer() {
helper.ensureJavascriptInited();

if (!hasFunction("render")) {
Expand All @@ -146,11 +148,13 @@ protected Renderer<JsonValue> createRenderer() {
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) {
Expand All @@ -159,7 +163,7 @@ private JavaScriptObject getJsCell(CellReference<?> cell) {
}

public native void render(JavaScriptObject wrapper,
JavaScriptObject cell, JavaScriptObject data)
JavaScriptObject cell, Object data)
/*-{
wrapper.render(cell, data);
}-*/;
Expand Down Expand Up @@ -262,7 +266,7 @@ private native boolean onBrowserEvent(JavaScriptObject wrapper,
}

@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;
}
Expand Down
Expand Up @@ -55,20 +55,24 @@ protected void setup(VaadinRequest request) {
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);
Item item = container.addItem(itemId);
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);

grid.getColumn("bean").setRenderer(new MyBeanJSRenderer());
grid.getColumn("bean").setWidth(250);

grid.getColumn("string").setRenderer(new JavaScriptStringRenderer());

addComponent(grid);
}

Expand Down
Expand Up @@ -34,9 +34,13 @@ public void testJavaScriptRenderer() {
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"));

Expand Down
@@ -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);
}

}
@@ -0,0 +1,5 @@
com_vaadin_tests_components_grid_JavaScriptStringRenderer = function() {
this.render = function(cell, data) {
cell.element.textContent = data;
}
}

0 comments on commit 8f81ba9

Please sign in to comment.