Page 1 of 1

DynamicTooltip on vector.Line (contentProvider issue)

Posted: Fri Feb 19, 2016 12:40 pm
by tisptv
Hello,

I have a question / issue with the following scenario:
The application has a track with several hundreds (thousands) of individual points - each containing a lot of additional information -.

So the line is drawn ('com.ptvag.webcomponent.map.vector.Line') and a DynamicTooltip ('com.ptvag.webcomponent.map.vector.DynamicTooltip') is "attached" to it, to get and show the full blown information then.

But here's the problem: When the map is zoomed out, the 'contentProvider' callback functions 'hover event' data 'lineSegment' member does not indicate the "original" segment index, but an index to a shorter "optimized" line.

Is there any way to get the "original" segment index?
Or can I somehow listen only to the "points" of 'vector.Line's?

The following example shows the effect (Paste it into the tutorial "playground"):
At the preset zoom level (18), the optimized line only creates callbacks with lineSegments between 0 and 49.
Once you zoom in, the callback gets correct lineSegments between 0 and 99!

Code: Select all

<html>
  <head>
    <!--[if IE]><script type="text/javascript" src="webcomponent/script/excanvas.js"></script><![endif]-->
    <script type="text/javascript" src="webcomponent/script/qooxdoo/script/qx-transport.js"></script>
    <script type="text/javascript" src=".qxrpc"></script>
    <script type="text/javascript" src="webcomponent/script/map.js"></script>

    <script type="text/javascript">
      function init() {
        var container = document.getElementById("mapContainer");
        var map = new com.ptvag.webcomponent.map.Map(container);
        window.onresize = function() {
          map.updateSize();
        };

        map.setCenter({x:4303250, y:5486500});
        map.setZoom(18);

        var vectorLayer = map.getLayer("vector");

        // create 100 segment line
        var lineCoords = [];
        var x = 4303250,
            y = 5486500;
        var fX = function (x) { return 200 * x; },
         // fY = function (y) { return 200 * y; }; "straight"
            fY = function (y) { return 200 * (y%2 ? y : y-1); }; "stair-step"
        for (var i = 0; i < 100; ++i) {
          lineCoords.push( x+fX(i), y+fY(i) );
        }
                          
        var line = new com.ptvag.webcomponent.map.vector.Line();
        line.setCoordinates(lineCoords);
        line.setPixelSize(8);
        line.setArrowsOnLine(true);
        vectorLayer.addElement(line);

        var contentProvider = function (tooltip, data) {
          return JSON.stringify({
            zoom : map.getZoom(),
            lnSeg: data.lineSegment
          });
        };

        var tooltip = new com.ptvag.webcomponent.map.vector.DynamicTooltip();
        tooltip.setContentProvider(contentProvider);
        tooltip.setAttachedElement(line);
        vectorLayer.addElement(tooltip);
      }

      qxp.dev.log.Logger.ROOT_LOGGER.setMinLevel(qxp.dev.log.Logger.LEVEL_INFO);
      qxp.dev.log.Logger.getClassLogger(qxp.core.Init).setMinLevel(qxp.dev.log.Logger.LEVEL_ERROR);
    </script>
  </head>

  <body onload="init()">
    <div id="mapContainer"
      style="width:100%;height:100%">
    </div>
  </body>
</html>
Thanks for any input / help
Peter

Re: DynamicTooltip on vector.Line (contentProvider issue)

Posted: Fri Feb 19, 2016 10:38 pm
by Bernd Welter
Hello Peter,

I forwarded your question to the ajaxmaps guru - he's probably answering the next week ;-)

Have a nice weekend!

Best regards Bernd

Re: DynamicTooltip on vector.Line (contentProvider issue)

Posted: Tue Feb 23, 2016 3:30 pm
by AndreasJunghans
Hi Peter,

the lines are optimized for fast drawing. If you want to get back the original segments/points (independent of zoom level), you have to modify the Line class. In the API documentation, there's a "Source" link that allows you to download the original JavaScript code for the class. You can then save this code, rename the class, make the necessary modifications, and include this new script in your own web application.

There are two ways to modify the code according to your needs:

1.) You can disable the zoom-based optimization by removing the "if (dist < 1)" check. However, this can result in poor performance depending on the number of lines/segments you're adding to the map.

2.) You can store additional information (similar to "setPixelCoordinates") that contains the original segment index for every segment of the zoom-optimized line. These additional indices can then be passed on to the tooltips (see "extendedEventInfo" in the code).

If you want to determine the line point that's closest to the cursor position, take a look at "getSquareDistance" in the Line class. By default it only determines the distances to the line segments (not the points) and picks the closest one, but you can modify it to calculate the distances to the line points instead (or in addition to the segments).

Hope this helps,

Andreas

Re: DynamicTooltip on vector.Line (contentProvider issue)

Posted: Tue Feb 23, 2016 6:53 pm
by tisptv
AndreasJunghans wrote:Hi Peter,

the lines are optimized for fast drawing. If you want to get back the original segments/points (independent of zoom level), you have to modify the Line class.
"Modify" is a nice description for "replace" ;)
AndreasJunghans wrote:In the API documentation, there's a "Source" link that allows you to download the original JavaScript code for the class. You can then save this code, rename the class, make the necessary modifications, and include this new script in your own web application.
I did this with 7 (!!!) classes already. The amount of PTV-code goes down ;)
What I really see as a problem here is: Each time an update (bugfix) to one of the original -PTV- classes is done, my application will not benefit from it 'cause the classes are fully replaced by my versions...
AndreasJunghans wrote: There are two ways to modify the code according to your needs:

1.) You can disable the zoom-based optimization by removing the "if (dist < 1)" check. However, this can result in poor performance depending on the number of lines/segments you're adding to the map.

2.) You can store additional information (similar to "setPixelCoordinates") that contains the original segment index for every segment of the zoom-optimized line. These additional indices can then be passed on to the tooltips (see "extendedEventInfo" in the code).

If you want to determine the line point that's closest to the cursor position, take a look at "getSquareDistance" in the Line class. By default it only determines the distances to the line segments (not the points) and picks the closest one, but you can modify it to calculate the distances to the line points instead (or in addition to the segments).

Hope this helps,

Andreas
Thanks for the clarification (and YES, it helps!)
Peter