Optimization of Kirby-Javascript interaction

So, I’ve advanced from this and now I’m trying to figure out how to best tell Javascript where it’s running from with Kirby.

Basically: my Javascript scripts contain a list of image files (which might be located in the same folder, or in a child folder). Because the scripts may be called from multiple locations into multiple pages, I’m trying to work with a flexible address system (what I’m trying to avoid, is having the addresses in the Javascript scripts be absolute ie “[site]/dog.jpg” because everything would break at the first misplaced folder and I’d have to change the addresses when working locally).

In other words, I want Kirby to calculate [site] (= the script’s location) and give it to Javascript, potentially more than once on a single page (thus, with a different [site] value for each script since they will have different locations). Then in Javascript I’d just have to concatenate [site] and relative addresses.

I’ve already tried doing this (below), but it doesn’t work because php just recalculates $currentcontext each time and the only one that remains at the end is the last one (since Javascript doesn’t start running before PHP is done).

<script>var context = "<?php  $currentcontext ?>"</script>

And then I figured I should just ask around about this, because although I can imagine ways to achieve this (for instance, using a different name for $currentcontext every time), I’d like to try and code this cleanly and I don’t have any clue what would be considered clean here.

Any suggestion?

Where do you set $currentcontext? In your controller or in your template? What is this value set to each time?

Sorry for delayed answer, a computer problem got in the way.

At first, I was thinking of defining currentContext within the tag, but this is not working (when the script does run, it returns an undefined variable error). I think it’s “simply” a matter of the javascript within the tag being run on server side, rather than client side (so the variables defined on the server don’t matter to the client)?

<?php

kirbytext::$tags['turbo'] = array(
  'attr' => array(
    'canvas',
    'width',
    'height'
  ),
  'html' => function($tag) {

    $turbo = $tag->attr('turbo');
    $baseurl = url() . '/' . $tag->page()->uri() . '/'; // This is $currentContext.
    $url = $baseurl .  $turbo;
    $canvas = $tag->attr('canvas');
    $width = $tag->attr('width', 720);
    $height = $tag->attr('height', 540);

    return '<script src="' . $url . '"></script><script>var currentContext = ' . $baseurl;'</script><canvas id="' . $canvas . '" width=' . $width . ' height= ' . $height . '></canvas>';
  }
);
?>

Tag above, Javacript below (Javascript truncated to focus on the tricky part).

for (i = 0; i < media.length; i++) {
        if (media[i].type === "Bitmap") {
            window[media[i].ref] = new createjs.Bitmap(currentContext + media[i].url);
        }
    }

I’m looking for a way to transfer $baseurl to the Javascript file client-side, summoned by PHP server-side.

Can’t you pass this via a data-attribute, e.g. data-baseurl="<?php echo $baseurl ?>" on the canvas element that you fetch in your javascript?

Also your code has a typo in it. Instead of:

...currentContext = ' . $baseurl;'...

you need:

...currentContext = ' . $baseurl . '...

Otherwise output stops after the semicolon. The dot will add the following string to the returned string.

You can find issues like this when looking at the source code in your browser.

Ooh, I didn’t know this existed! Thanks, this is helping a lot - I am slowly advancing.

lukasbestle > Thanks for the pointer :slight_smile: