When providing dynamic point coordinates, why is the syntax "function() {return xxx}" mandatory?

358 views
Skip to first unread message

Cleonis

unread,
Sep 27, 2014, 2:58:15 PM9/27/14
to jsxg...@googlegroups.com
Illustrating jsfiddle:
http://jsfiddle.net/Cleonis/y76d2xga/

As you know, my graphlets are pretty much always animations, and pretty much always include a slider.

For the purpose of code organize I prefer to do all calculation in the 'playing' loop, with the graph elements simply calling the results of those calculations.

For example: if I want to make a point move along a circular trajectory I'd like to code in the playing loop:

x = Math.cos(angle);
y = Math.sin(angle);

And then for the moving point:

var p = board.create(
  'point',
  [x,  y]
);

I tried that, but then the point doesn't move. I surmise that when executing a board.Update() JSXGraph does not update elements that have their coordinates in the above form.


To get the motion I have to code:

var p = board.create(
  'point',
  [function() {return x}, function() {return y}]
);

That is not a problem of course, but I'm always on the look for cleaner, more economical code. I'd like to have the short form available.


I'm guessing that you use the "function() {return x}" syntax as a triggering device, setting things up in such a way that if JSXGraph encounters the "function() {return xxx}" form it proceeds to recompute and redraw, rather than leave the element untouched. Am I guessing correctly?

Cleon Teunissen






Alfred Wassermann

unread,
Sep 30, 2014, 7:09:39 AM9/30/14
to jsxg...@googlegroups.com
In JSXGraph the coordinates of a point are newly computed in every update of the board. Internally, coordinates of a point are functions. The "exceptional case" of free points, means the functions return constants which are changed when the user drags the point. So, for example an intersection point of two lines possesses as functions the intersection functions of the two lines. Therefore, it was an easy step to allow arbitrary functions for the coordinates.

In you first example

x = Math.cos(angle);
y
= Math.sin(angle);

var p = board.create(
 
'point',
 
[x,  y]
);

the point will be a free point having the initial coordinates [x,y]. Allowing to use arbitrary JavaScript functions as parameters for an object gives JSXGraph a lot of freedom.
By the way, also some attributes like colors or strokeWidth can have functions as values. See for example http://jsxgraph.uni-bayreuth.de/wiki/index.php/Hypotrochoid

Best wishes,
Alfred

Cleonis

unread,
Oct 1, 2014, 3:14:15 PM10/1/14
to jsxg...@googlegroups.com
Alfred Wassermann wrote:
By the way, also some attributes like colors or strokeWidth can have functions as values. See for example http://jsxgraph.uni-bayreuth.de/wiki/index.php/Hypotrochoid

It occurred to me that in effect all attributes of JSXGraph elements are dynamic.
http://jsfiddle.net/Cleonis/nzaw7yv1/

In the above jsfiddle the function 'strokeWidthMod' changes the lineWidth property of the line object that is in the graph.
I haven't tried it, but I presume this way of modifying will work for every property of every object.


Returning to my original question:

This syntax:


var p = board.create(
  'point',
  [function() {return x}, function() {return y}]
);

forces the JSXGraph engine to resolve the input.

Currently, when this syntax is used:

var p = board.create(
  'point',
  [x,  y]
);

x and y are not resolved (instead the initial values are reused, which goes against my expectation).
My suggestion is to make the JSXGraph engine resolve the input in both cases.

(I know, my question arises from ignorence. My expectation is that variables get resolved. That is what I see the Javascript engine do: variables get resolved.)


Cleon Teunissen

Alfred Wassermann

unread,
Oct 2, 2014, 3:37:23 AM10/2/14
to jsxg...@googlegroups.com
Ok, in your example you are using setAttribute to set dynamically some attributes. But the JSXGraph is more general, attributes can have functions as values:
var line = board.create(
 
'line',
 
[[-1, -1.25], [1, -1.25]],
 
{strokeColor:'#888',
   highlight
:false,
   straightFirst
:false,
   straightLast
:false,
   strokeWidth
:function() {
         
return parseInt(10*Math.abs( Math.cos(phase)), 10);
       
}
   
}
);

In that way, the attribute is dynamic, while the programmer needs not to care about updates.

Your example

var p = board.create(
  'point',
  [x,  y]
);

is needed to have an easy way to provide a static element.
Best wishes,
Alfred




Reply all
Reply to author
Forward
0 new messages