ASE Home Page Products Download Purchase Support About ASE
ChartDirector General
Forum HomeForum Home   SearchSearch

Message ListMessage List     Post MessagePost Message

  SVG Image Maps
Posted by Carl Thompson on Sep-20-2009 01:57
Hi Peter,

Thanks for adding SVG support in ver 5.0.

Any recommendations on how to make vector SVG images "clickable"?

This would essentially provide functionality that is roughly equivalent to image maps used with <img> tags ... but presumably could be generated on the fly (i.e., not require building the image, then generating the image map).

This would make SVG a better option for dynamic creation of clickable charts -- especially with the ability for the client to zoom in on the image and not loose resolution or "click" functionality.

I am using PHP version, if there is an example available.

Thanks

  Re: SVG Image Maps
Posted by Peter Kwan on Sep-20-2009 18:52
Hi Carl,

Unluckily, currently SVG charts are not clickable.

Most SVG viewer supports zooming without losing resolution by itself, although what they mean by "zooming" may not be what you expect.

(Zooming a chart is like zooming a map. Zooming without losing resolution may not be sufficient. We need zooming with increasing resolution. For example, if you zoom in the google map, you can see more and more details, not just the same map drawn bigger. This type of zooming cannot be helped with SVG. Currently, the ChartDirector zooming framework can already achieve zooming with increasing details, although the zoomable chart image is raster based, just like google map.)

Regards
Peter Kwan

  Re: SVG Image Maps
Posted by Carl Thompson on Sep-20-2009 19:56
Clickable SVG would be a great feature.  The shapes within the vector SVG can easily be surrounded with hyperlinks, thus providing an Image Map capability while avoiding the need to generate and use a separate <map><area />...</map> block.

I mentioned zooming more as it relates to:
(1) <a> tags around SVG shapes would still work no matter how much zoom is applied, and;
(2) it appears that the latest versions of the major browsers all support "zoom" (or auto scaling if you prefer) without any pixelation i.e., single SVG images/charts are "zoomed" to the size of the browser window automatically with the additional levels of detail that you would expect from a vector image. This also appears to translate well when printing from the browser ...  meaning that I am able to print single SVG vector charts that "fill" the page (landscape mode) without loss of detail (printed in color at 600dpi), even when the original screen version of the generated chart was 350x220 at 72dpi.  Note that this is not possible with other image formats.

  Re: SVG Image Maps
Posted by Carl Thompson on Jan-05-2010 03:20
Hi Peter,

Some more ammo re: need for "click" and "hover" support in SVG.

Adding these capabilities to generated SVG images is available by adding support for <a>
tags around graphic objects.  Since SVG is just XML, I have looked at injecting <a> tags
around image objects after the image is returned by ChartDirector ... although "do-able" I
am really hoping that you'll see the value in supporting this capability directly as an
alternative to creating image maps, which right now, do not work with SVG.

Another advantage of using SVG is that load times on a page with multiple images and
image maps is orders of magnitude slower than the same page without image maps.  So the
creation and loading of image maps adds significant overhead that would/could be
dramatically reduced by simply surrounding SVG objects with <a> tags and avoiding the
overhead of creating separate image maps data.

Also ... SVG can be more accessible ...
http://www.w3.org/TR/SVG-access/
... which is increasingly becoming a requirement, where separate data tables alone cannot
ensure conformity.

  Re: SVG Image Maps
Posted by Peter Kwan on Jan-05-2010 18:10
Hi Carl,

SVG charts with clickable objects and tooltips are in our wish list. We will implement this in a future version of ChartDirector. However, we cannot provide a confirm schedule yet.

If you thinking adding image maps to charts make the web page slower, it is because your charts have a lot of clickable things or tooltips. For example, each clickable object or tooltip may consume around 100 bytes (depending on the length of the clickable URL or the tooltip text). If you have 10000 clickable objects or tooltips in the charts, it will take up 1 Mbytes.

Using <A> tags in SVG will not make it faster. You still need the same number of URL and tooltips, and therefore similar number of bytes.

Also, the simple method of using <A> tags around SVG objects will not work in general. It is because a clickable chart entity is not the same as an SVG object. A clickable chart entity may be a combination of multiple SVG objects (eg. a 3D bar segment is composed of multiple polygons), or it may be part of a SVG object (eg. a line segment in a line chart is part of a SVG polyline). So there is no one to one relationship between SVG objects and chart entities. A method that works in general may be much more complicated.

Regards
Peter Kwan

  Re: SVG Image Maps
Posted by Carl Thompson on Sep-19-2016 03:24
Hi Peter ... it's been a long time ... still could use a solution for combining Image Map functionality with vector SVG images.  Despite HTML5 support for USEMAP in <IMG> and <OBJECT> tags it just doesn't work when the Image is SVG ... and so what are the options?  Are there any?  Support for xlinks in the SVG itself (definable areas and actions) would be ideal ... but if there is any way to this I am interested in knowing how.  Thanks.
Peter Kwan wrote:

Hi Carl,

Unluckily, currently SVG charts are not clickable.

Most SVG viewer supports zooming without losing resolution by itself, although what they mean by "zooming" may not be what you expect.

(Zooming a chart is like zooming a map. Zooming without losing resolution may not be sufficient. We need zooming with increasing resolution. For example, if you zoom in the google map, you can see more and more details, not just the same map drawn bigger. This type of zooming cannot be helped with SVG. Currently, the ChartDirector zooming framework can already achieve zooming with increasing details, although the zoomable chart image is raster based, just like google map.)

Regards
Peter Kwan

  Re: SVG Image Maps
Posted by Peter Kwan on Sep-20-2016 04:58
Attachments:
Hi Carl,

In most modern browsers, image map works with the <IMG> tag regardless of the image type. You can use SVG as the image type and the image map will work normally as according to the HTML standard.

According to the HTML standard, if you resize the image (eg. by using CSS "width" and "height"), the image map will not be automatically resized. This is the case no matter PNG, JPG or SVG is used. This means the image map may no longer match the <IMG> tag. As there is no CSS attribute to resize the image map, to make the image map matching the resized <IMG>, the only method I can think of is to use Javascript to adjust all the image map coordinates whenever the <IMG> size changes.

The ChartDirector Javascript library "cdjcv.js" actually an undocumented functions JsChartViewer.initToolTipHandler to automatically resize the image map to match the <IMG> size. I have attached an example based on the Simple Clickable Chart" sample code for your reference. Please compare the attached code with the original sample code to see the added code to automatically resize the image map.

#Original Sample Code
http://www.advsofteng.com/doc/cdphp.htm#simpleclickable.htm

Hope this can help.

Regards
Peter Kwan
clickbar.php
<?php
require_once("../lib/phpchartdir.php");

# The data for the bar chart
$data = array(450, 560, 630, 800, 1100, 1350, 1600, 1950, 2300, 2700);

# The labels for the bar chart
$labels = array("1996", "1997", "1998", "1999", "2000", "2001", "2002", "2003", "2004", "2005");

# Create a XYChart object of size 600 x 360 pixels
$c = new XYChart(600, 360);

# Add a title to the chart using 18pt Times Bold Italic font
$c->addTitle("Annual Revenue for Star Tech", "timesbi.ttf", 18);

# Set the plotarea at (60, 40) and of size 500 x 280 pixels. Use a vertical gradient color from
# light blue (eeeeff) to deep blue (0000cc) as background. Set border and grid lines to white
# (ffffff).
$c->setPlotArea(60, 40, 500, 280, $c->linearGradientColor(60, 40, 60, 280, 0xeeeeff, 0x0000cc), -1,
    0xffffff, 0xffffff);

# Add a multi-color bar chart layer using the supplied data. Use soft lighting effect with light
# direction from top.
$barLayerObj = $c->addBarLayer3($data);
$barLayerObj->setBorderColor(Transparent, softLighting(Top));

# Set x axis labels using the given labels
$c->xAxis->setLabels($labels);

# Draw the ticks between label positions (instead of at label positions)
$c->xAxis->setTickOffset(0.5);

# When auto-scaling, use tick spacing of 40 pixels as a guideline
$c->yAxis->setTickDensity(40);

# Add a title to the y axis with 12pt Times Bold Italic font
$c->yAxis->setTitle("USD (millions)", "timesbi.ttf", 12);

# Set axis label style to 8pt Arial Bold
$c->xAxis->setLabelStyle("arialbd.ttf", 8);
$c->yAxis->setLabelStyle("arialbd.ttf", 8);

# Set axis line width to 2 pixels
$c->xAxis->setWidth(2);
$c->yAxis->setWidth(2);

# Create the image and save it in a temporary location
$chart1URL = $c->makeSession("chart1", SVG);

# Create an image map for the chart
$imageMap = $c->getHTMLImageMap("clickline.php", "", "title='{xLabel}: US\$ {value|0}M'");
?>
<!DOCTYPE html>
<html>
<head>
<script type="text/javascript" src="cdjcv.js"></script>
</head>
<body style="margin:5px 0px 0px 5px">
<script type="text/javascript">

JsChartViewer.addEventListener(window, 'load', function() {
    var viewer = JsChartViewer.get('chart1');
    viewer.originalWidth = <?php echo $c->getWidth(); ?>;
    viewer.originalHeight = <?php echo $c->getHeight(); ?>;
    viewer.initToolTipHandler();
});
</script>
<div style="font-size:18pt; font-family:verdana; font-weight:bold">
    Simple Clickable Bar Chart
</div>
<hr style="border:solid 1px #000080" />
<div style="font-size:10pt; font-family:verdana; margin-bottom:20">
    <a href="viewsource.php?file=<?php echo $_SERVER["SCRIPT_NAME"]?>">View Source Code</a>
</div>
<img id="chart1" src="getchart.php?<?php echo $chart1URL?>" border="0" usemap="#map1">
<map name="map1">
<?php echo $imageMap?>
</map>
</body>
</html>

  Re: SVG Image Maps
Posted by Carl Thompson on Sep-21-2016 23:14
Thanks Peter ...

It doesn't appear to work unless the SVG image is really a PNG (or something other than original vector SVG) wrapped/embedded (whatever it is called) in an SVG.  Unless I am missing something?  Do you have an example where the SVG image generated is a real vector SVG image combined with an image map?

Cheers, Carl
Peter Kwan wrote:

Hi Carl,

In most modern browsers, image map works with the <IMG> tag regardless of the image type. You can use SVG as the image type and the image map will work normally as according to the HTML standard.

According to the HTML standard, if you resize the image (eg. by using CSS "width" and "height"), the image map will not be automatically resized. This is the case no matter PNG, JPG or SVG is used. This means the image map may no longer match the <IMG> tag. As there is no CSS attribute to resize the image map, to make the image map matching the resized <IMG>, the only method I can think of is to use Javascript to adjust all the image map coordinates whenever the <IMG> size changes.

The ChartDirector Javascript library "cdjcv.js" actually an undocumented functions JsChartViewer.initToolTipHandler to automatically resize the image map to match the <IMG> size. I have attached an example based on the Simple Clickable Chart" sample code for your reference. Please compare the attached code with the original sample code to see the added code to automatically resize the image map.

#Original Sample Code
http://www.advsofteng.com/doc/cdphp.htm#simpleclickable.htm

Hope this can help.

Regards
Peter Kwan

  Re: SVG Image Maps
Posted by Peter Kwan on Sep-22-2016 03:15
Attachments:
Hi Carl,

Sorry for this problem. I tested again and found out the code does not work in the released version of ChartDirector for PHP. It only works in my test machine due to using a different version of the Javascript library.

I have modified the code and now it should work. Note that it only works with ChartDirector 6.0, and the "cdjcv.js" should also be from ChartDirector 6.0. The file date of the "cdjcv.js" should be around "Jun 1, 2015".

I also found out in IE 11, the <IMG> must be given a size for the SVG to work normally. It may be because the SVG itself is scalable and does not have a definite size so the IE 11 is confused which size to use to display the image. For Chrome and FireFox, if no size is given, the SVG simply fills up the browser window. To make the SVG work in IE 11, I have given it a size of 50% of the container by using the style sheet entry "#chart1 {width:50%;}". In this way, you can see the chart resizes as the browser window resizes and can verify that the image map continues to work.

Hope this can help.

Regards
Peter Kwan
clickbar.php
<?php
require_once("../lib/phpchartdir.php");

# The data for the bar chart
$data = array(450, 560, 630, 800, 1100, 1350, 1600, 1950, 2300, 2700);

# The labels for the bar chart
$labels = array("1996", "1997", "1998", "1999", "2000", "2001", "2002", "2003", "2004", "2005");

# Create a XYChart object of size 600 x 360 pixels
$c = new XYChart(600, 360);

# Add a title to the chart using 18pt Times Bold Italic font
$c->addTitle("Annual Revenue for Star Tech", "timesbi.ttf", 18);

# Set the plotarea at (60, 40) and of size 500 x 280 pixels. Use a vertical gradient color from
# light blue (eeeeff) to deep blue (0000cc) as background. Set border and grid lines to white
# (ffffff).
$c->setPlotArea(60, 40, 500, 280, $c->linearGradientColor(60, 40, 60, 280, 0xeeeeff, 0x0000cc), -1,
    0xffffff, 0xffffff);

# Add a multi-color bar chart layer using the supplied data. Use soft lighting effect with light
# direction from top.
$barLayerObj = $c->addBarLayer3($data);
$barLayerObj->setBorderColor(Transparent, softLighting(Top));

# Set x axis labels using the given labels
$c->xAxis->setLabels($labels);

# Draw the ticks between label positions (instead of at label positions)
$c->xAxis->setTickOffset(0.5);

# When auto-scaling, use tick spacing of 40 pixels as a guideline
$c->yAxis->setTickDensity(40);

# Add a title to the y axis with 12pt Times Bold Italic font
$c->yAxis->setTitle("USD (millions)", "timesbi.ttf", 12);

# Set axis label style to 8pt Arial Bold
$c->xAxis->setLabelStyle("arialbd.ttf", 8);
$c->yAxis->setLabelStyle("arialbd.ttf", 8);

# Set axis line width to 2 pixels
$c->xAxis->setWidth(2);
$c->yAxis->setWidth(2);

# Create the WebChartViewer object
$viewer = new WebChartViewer("chart1");
$viewer->setCustomAttr(31, $c->getWidth());
$viewer->setCustomAttr(32, $c->getHeight());


# Output the chart
$chartQuery = $c->makeSession($viewer->getId(), SVG);

# Set the chart URL to the viewer
$viewer->setImageUrl("getchart.php?".$chartQuery);

# Create an image map for the chart
$viewer->setImageMap($c->getHTMLImageMap("clickline.php", "", "title='{xLabel}: US\$ {value|0}M'"));
?>
<!DOCTYPE html>
<html>
<head>
<script type="text/javascript" src="cdjcv.js"></script>
<style>
#chart1 {width:50%;}
</style>
</head>
<body style="margin:5px 0px 0px 5px">
<script type="text/javascript">

JsChartViewer.addEventListener(window, 'load', function() {
    var viewer = JsChartViewer.get('chart1');
    //viewer.setCustomAttr(31, <?php echo $c->getWidth(); ?>);
    //viewer.setCustomAttr(32, <?php echo $c->getHeight(); ?>);
    viewer.initToolTipHandler();
});
</script>
<div style="font-size:18pt; font-family:verdana; font-weight:bold">
    Simple Clickable Bar Chart
</div>
<hr style="border:solid 1px #000080" />
<div style="font-size:10pt; font-family:verdana; margin-bottom:20">
    <a href="viewsource.php?file=<?php echo $_SERVER["SCRIPT_NAME"]?>">View Source Code</a>
</div>
<!-- ****** Here is the chart image ****** -->
<?php echo $viewer->renderHTML()?>
</body>
</html>

  Re: SVG Image Maps
Posted by Carl Thompson on Sep-22-2016 04:35
Hi Peter ... Thanks for the followup ... but I think there is some level of miscommunication.

This example is still, in essence, creating a PNG

Inside the SVG there is a single <g> node with xlink:href="data:image/png;..."

The problem with this example, in fact any example I have tried in combination with an image map, is that the code does not produce a true vector image and therefore it does not look nice at different sizes.

What I am after is an option to have an Image Map with an SVG that is not a PNG (or .jpg or any other bitmap image) but a true original vector graphic.

Not sure if getchart.php is the issue (also tried using the V6.0 of getchart.php) or if Image Maps just won't work if the image is a vector SVG ... but if it does work (is supported) ideally you can share a link to a working example (<img or <object are ok) where the image is a true vector graphic SVG in combination with an Image Map.

Thanks!

Peter Kwan wrote:

Hi Carl,

Sorry for this problem. I tested again and found out the code does not work in the released version of ChartDirector for PHP. It only works in my test machine due to using a different version of the Javascript library.

I have modified the code and now it should work. Note that it only works with ChartDirector 6.0, and the "cdjcv.js" should also be from ChartDirector 6.0. The file date of the "cdjcv.js" should be around "Jun 1, 2015".

I also found out in IE 11, the <IMG> must be given a size for the SVG to work normally. It may be because the SVG itself is scalable and does not have a definite size so the IE 11 is confused which size to use to display the image. For Chrome and FireFox, if no size is given, the SVG simply fills up the browser window. To make the SVG work in IE 11, I have given it a size of 50% of the container by using the style sheet entry "#chart1 {width:50%;}". In this way, you can see the chart resizes as the browser window resizes and can verify that the image map continues to work.

Hope this can help.

Regards
Peter Kwan

  Re: SVG Image Maps
Posted by Peter Kwan on Sep-22-2016 21:36
Hi Carl,

I have uploaded the code to our web site so you can try it:

http://www.advsofteng.net/ChartDirector/phpdemo/clickbar.php

If the SVG is still an image, I suspect the ChartDirector in your server is still of version 5.x.

To upgrade ChartDirector 6.0, you would need to copy both the ChartDirector shared object "libchartdir.so" and the PHP extension "phpchartdir???.dll" to the PHP extension directory. Just copying "phpchartdir???.dll" would not work. Also, the directory has to be the PHP extension directory (or the directory that your PHP is actually using for extensions). For some PHP installations, you may need to restart the Apache web server (or other brands of web server).

To check the version of your ChartDirector, please modify the $c->addTitle line to:

$c->addTitle(dechex(getVersion()));

This will include the version in the chart title. The first digit is the major version number, which should be 6.

Hope this can help.

Regards
Peter Kwan

  Re: SVG Image Maps
Posted by Carl Thompson on Sep-23-2016 04:03
Thanks Peter ... got it ... have upgraded to V60.

Cheers, Carl