Created

Embed URL

HTTPS clone URL

SSH clone URL

You can clone with HTTPS or SSH.

Download Gist

Wicket and JFreeChart integration including image map for tooltips and clickable graph

View DynamicImageMap.java
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89
 
import org.apache.wicket.ajax.AjaxEventBehavior;
import org.apache.wicket.ajax.AjaxRequestTarget;
import org.apache.wicket.ajax.IAjaxCallDecorator;
import org.apache.wicket.ajax.calldecorator.CancelEventIfNoAjaxDecorator;
import org.apache.wicket.markup.ComponentTag;
import org.apache.wicket.markup.html.WebMarkupContainer;
import org.apache.wicket.markup.repeater.Item;
import org.apache.wicket.markup.repeater.RefreshingView;
import org.apache.wicket.markup.repeater.util.ModelIteratorAdapter;
import org.apache.wicket.model.IModel;
import org.apache.wicket.model.Model;
import org.jfree.chart.entity.ChartEntity;
 
import java.util.Collection;
import java.util.Iterator;
 
/**
* Wicket markup container that produces an image map dynamically
* from the given model
*
* @author Jonny Wray
*/
public abstract class DynamicImageMap extends WebMarkupContainer {
 
private String mapName;
 
public DynamicImageMap(String id, String mapName, IModel<Collection<ChartEntity>> model){
super(id, model);
this.mapName = mapName;
RefreshingView mapAreas = new RefreshingView("areas", model){
 
@Override
protected Iterator getItemModels() {
Collection<ChartEntity> chartEntityCollection = (Collection<ChartEntity>)getDefaultModelObject();
return new ModelIteratorAdapter(chartEntityCollection.iterator()){
@Override
protected IModel model(Object object) {
return new Model((ChartEntity)object);
}
};
}
 
@Override
protected void populateItem(Item item) {
final ChartEntity entity = (ChartEntity)item.getModelObject();
WebMarkupContainer area = new WebMarkupContainer("area"){
 
@Override
protected void onComponentTag(final ComponentTag tag){
super.onComponentTag(tag);
assert tag.getName().equals("area");
tag.put("shape", entity.getShapeType());
tag.put("coords", entity.getShapeCoords());
tag.put("href", "#");
String tooltipText = entity.getToolTipText();
if(tooltipText != null && !tooltipText.isEmpty()){
tag.put("title", tooltipText);
}
}
};
area.add(new AjaxEventBehavior("onclick"){
private static final long serialVersionUID = 2615093257359874075L;
 
@Override
protected void onEvent(AjaxRequestTarget target) {
onClickCallback(target, entity);
}
 
protected IAjaxCallDecorator getAjaxCallDecorator(){
return new CancelEventIfNoAjaxDecorator();
}
 
});
item.add(area);
}
};
add(mapAreas);
}
 
public abstract void onClickCallback(AjaxRequestTarget target, ChartEntity entity);
 
@Override
protected void onComponentTag(final ComponentTag tag){
super.onComponentTag(tag);
assert tag.getName().equals("map");
tag.put("name", mapName);
}
}
View DynamicImageMap.java
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66
 
import org.apache.wicket.markup.html.image.resource.BufferedDynamicImageResource;
import org.apache.wicket.markup.html.image.resource.DynamicImageResource;
import org.jfree.chart.ChartRenderingInfo;
import org.jfree.chart.JFreeChart;
import org.jfree.chart.entity.ChartEntity;
import org.jfree.chart.entity.EntityCollection;
 
import java.awt.image.BufferedImage;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.Collection;
 
/**
* Bean that holds the information and logic needed to render
* a JFreeChart to an image. Used as a model object to enable
* dynamic redrawing of an chart image.
*
* @author Jonny Wray
*/
public class JFreeChartRenderingBean implements Serializable{
private ChartRenderingInfo renderingInfo = new ChartRenderingInfo();
private BufferedDynamicImageResource imageResource;
private JFreeChart chart;
private int width;
private int height;
 
/**
* Construct the rendering bean
*
* @param chart The chart to render
* @param width The width to render to
* @param height The height to render to
*/
public JFreeChartRenderingBean(JFreeChart chart, int width, int height){
this.chart = chart;
this.width = width;
this.height = height;
}
 
public DynamicImageResource getImageResource(){
if(imageResource == null){
renderingInfo.clear();
BufferedImage image = chart.createBufferedImage(width, height, renderingInfo);
imageResource = new BufferedDynamicImageResource();
imageResource.setImage(image);
}
return imageResource;
}
 
public Collection<ChartEntity> getChartEntities(){
if(imageResource == null){
getImageResource(); // Force the image to be rendered
}
Collection<ChartEntity> chartEntities = new ArrayList<ChartEntity>();
EntityCollection entities = renderingInfo.getEntityCollection();
if (entities != null) {
int count = entities.getEntityCount();
for (int i = count - 1; i >= 0; i--) {
ChartEntity entity = entities.getEntity(i);
chartEntities.add(entity);
}
}
return chartEntities;
}
}
View DynamicImageMap.java
1 2 3 4 5 6 7 8 9 10 11 12 13 14
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xmlns:wicket="http://wicket.apache.org/dtds.data/wicket-xhtml1.3-strict.dtd" xml:lang="en" lang="en">
<wicket:panel>
<span>
<img style="vertical-align: middle;" wicket:id="image" />
<map wicket:id="imageMap" >
<span wicket:id="areas">
<area wicket:id="area" />
</span>
</map>
</span>
</wicket:panel>
</html>
View DynamicImageMap.java
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47
 
import org.apache.wicket.AttributeModifier;
import org.apache.wicket.ajax.AjaxRequestTarget;
import org.apache.wicket.markup.html.image.NonCachingImage;
import org.apache.wicket.markup.html.panel.Panel;
import org.apache.wicket.model.IModel;
import org.apache.wicket.model.Model;
import org.apache.wicket.model.PropertyModel;
import org.jfree.chart.entity.ChartEntity;
 
import java.util.UUID;
 
/**
* Wicket panel that includes a JFreeChart as an image with an
* associated image map used for tooltips and clicks.
*
* @author Jonny Wray
*/
public class MappedJFreeChartPanel extends Panel {
 
public MappedJFreeChartPanel(final String id, final IModel<JFreeChartRenderingBean> model){
super(id, model);
String mapName = getPath() + UUID.randomUUID().toString(); // UUID allows use in a repeater
 
NonCachingImage chartImage = new NonCachingImage("image", new PropertyModel(model, "imageResource"));
chartImage.add(new AttributeModifier("usemap", true, new Model("#"+mapName)));
add(chartImage);
DynamicImageMap imageMap = new DynamicImageMap("imageMap", mapName, new PropertyModel(model, "chartEntities")){
@Override
public void onClickCallback(AjaxRequestTarget target, ChartEntity entity) {
onClick(target, entity);
}
};
add(imageMap);
}
 
/**
* Do nothing implementation of an onClick callback for a chart entity. Override to
* implement Ajax onclick functionality
*
* @param target The Ajax request
* @param entity The chart entity clicked on
*/
protected void onClick(AjaxRequestTarget target, ChartEntity entity){
 
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Something went wrong with that request. Please try again.