Hi,
the solution from the wiki keeps the buffered image in the component
tree, that's not a good idea (probably this is why it's transient).
The actual problem is, that all markup (including your refreshingView)
is rendered first. Then the browser pulls the image data in a second
request.
Simplest solution is to render twice, once just to get the
ChartRenderingInfo, and a second time for the actual request for the
image data.
Another possibility is to:
- leave the area list empty at first
- render the chart image in the dynamic resource *and* keep the
ChartRenderingInfo in an instance variable (non-transient)
- have an AjaxEventBehavior("load") on the image, which re-renders the
refreshingView and updates the area with the kept ChartRenderingInfo
Have fun
Sven
On 03.11.21 18:38, C.S. wrote:
Dear wicket developers,
i try to integrate wicket with jfreechart. Wicket wiki contains an example
under
https://cwiki.apache.org/confluence/display/WICKET/JFreeChart+with+clickable+imagemap
but this code is 11 yrs old and does not work with current versions.
Speaking of versions: i must stick with jdk 1.8, which means i cannot
upgrade to wicket 9+
Using wicket version 8.12.0
Goal is to create a usemap list to an image, so image is clickable
(contains tooltips).
For image i use a NonCachingImage and for the usemap i use a RefreshingView.
Trouble is, when the RefreshingView renders, the image has no rendering
info yet. So the RefreshingView model is empty. Image creates its rendering
info very late - during onRequest(). RefreshingView is rendered long ago at
this time.
I tried to create the image rendering info before rendering the
RefreshingView.
This is how it works in the old wiki example. Unfortunately, the new
versions throw a StackOverflowException. During Serialization, some
JFreeChart methods interact with some Wicket serialization methods. They
call each other (via reflexion) some 100s of times until StackOverflow
occurs.
What would you suggest? Is there a way to refresh the RefreshingView
without ajax?
Or somehow render the RefreshingView after the image produced its rendering
info?
Or should i use different wicket components? Or wrap/enclose these
components under another component (which one? ).
Thank you for your help
Christos Stieglitz
My code:
HTML:
<img wicket:id="livedata" usemap="#skipper"/>
<map name="skipper">
<area wicket:id="area"/>
</map>
Java:
RefreshingView<ChartEntity> mapAreas = new RefreshingView<>("area") {
@Override
protected Iterator<IModel<ChartEntity>> getItemModels() {
...
// This is called during onRender(). List model is empty
return models.iterator();
}
@Override
protected void populateItem(Item<ChartEntity> item) {
ChartEntity entity = item.getModelObject();
item.add(new AttributeAppender("shape", entity.getShapeType()));
item.add(new AttributeAppender("coords", entity.getShapeCoords()));
item.add(new AttributeAppender("href", "#"));
item.add(new TooltipBehavior(entity.getToolTipText()));
}
};
mapAreas.setOutputMarkupId(Boolean.TRUE);
add(mapAreas);
NonCachingImage ch = new NonCachingImage("livedata", Model.of(chart)) {
@Override
protected DynamicImageResource getImageResource() {
return new DynamicImageResource() {
@Override
protected byte[] getImageData(IResource.Attributes attributes) {
ChartRenderingInfo renderingInfo = new ChartRenderingInfo();
// chart is a JFreeChart
BufferedImage imgbytes = chart.createBufferedImage(imgwidth,
imgheight, renderingInfo);
EntityCollection entities = renderingInfo.getEntityCollection();
// This is called very late, during onRequest().
// EntityCollection contains now everything is needed,
// but how to call
// RefreshingView.onRender() from here?
// If i put this code anywhere else i get
StackOverflowException.
return toImageData(imgbytes);
}
};
}
};
add(ch);
---------------------------------------------------------------------
To unsubscribe, e-mail: users-unsubscr...@wicket.apache.org
For additional commands, e-mail: users-h...@wicket.apache.org