Skip to main content
JEJoll
Known Participant
October 11, 2016
Question

Common JS Interface and WebGL

  • October 11, 2016
  • 1 reply
  • 1508 views

I'm not a Captivate Developer, but am responsible for writing some WebGL compatibility testing code for the courseware we are developing. I'm hoping to gain some insight into how to execute some custom javascript, and then show/hide some groups on a page based on the results of said javascript.

Basically, we will have two groups of content on a slide, one containing some Unity interactives that will be running in WebGL, another containing videos that will display if the user's browser is not WebGL compatible.

Since the user can navigate to any slide at any given time, I need to perform this compatibility check on each slide that contains the WebGL content.

What I want to do is:

When a page loads, execute some javascript that defines and executes some functions, which in turn set a variable isWebGLCompatible. Then I want to check whether this variable is true or false, and then show/hide the groups containing the appropriate content.

Is something like this possible inside captivate?

This topic has been closed for replies.

1 reply

TLCMediaDesign
Inspiring
October 11, 2016

I think you should create a variable for WebGL and run JavaScript on enter of the first slide to populate it as 0 or 1.

Then create conditional advanced actions to execute on enter of the slides in question to show/hide the applicable groups.

This could all be done dynamically with external JavaScript depending on how you name the elements within the groups. Note that there are no groups to reference in JavaScript.

JEJoll
JEJollAuthor
Known Participant
October 11, 2016

Unfortunately, we can't rely on setting the variable on the first slide, as the user has the freedom to return to any slide using bookmarks, etc.

I've got another solution using pure external js to set the variable, but it involves modifying Captivate's generated index.html file to reference the external js. This will work, but I'd like to avoid this solution if possible.

Is it possible to set the variable and then do the check all on one slide?

JEJoll
JEJollAuthor
Known Participant
February 7, 2017

Thanks for this answer. It is much appreciated. I have run into another issue with the Unity/WebGL in Captivate.

I have been working with this for awhile now. If you zip up the Unity WebGL output it goes in through the browse as a web object. My new issue: The webobject loads on the top layer of the iframe. Now adobe states:

In Adobe Captivate 9, web objects and HTML 5 animations (when layered with other shapes) always appear on top 

To work around this issue in HTML5, do the following:

  1. In your Captivate installation folder, open the AdobeCaptivate.ini file.
  2. Edit the file to change the value of UseWidget7 to 1 as follows:

UseWidget7=1
  3. Close and re-launch Adobe Captivate.

You can now position your web objects on top or bottom, and they appear as expected in HTML 5. 

Which I have done so my Captivate buttons etc appear on top. The bummer is that now my Unity controls don’t work? If I switch back to  UseWidget7=0  it is now on the top layer but the buttons work. Did you run into this?

Much thanks for any help.

Collene


We had a similar issue when we created our course. Unfortunately, I don't think there's a quick and easy fix.

It sounds like you have Captivate buttons which overlap your Unity content? We didn't encounter this specific problem, but we did have to do a bit of wizardry to make Unity and Captivate play nicely.

Captivate makes a lot of div tags in the HTML DOM, and I suspect that whatever div contains the buttons in question is also blocking interaction with Unity (I assume the Unity interactions are mouse clicks?).

Honestly, it would be a lot (and I mean A LOT) less effort to move the Captivate buttons to a location where they don't overlap Unity (or to resize Unity so it doesn't obscure the buttons).

If that's not an option, I would go with this route:

Remove those buttons from Captivate completely, and revert to having Unity sit on the top zIndex. Instead of having them embedded in Captivate, I would create the buttons either in the html file responsible for launching Unity (iframe), or programatically through custom JavaScript added to the captivate output after it's been published. Alternately, you could put the buttons directly inside of Unity.

If adding the buttons to the iframe or through javascript in the published Captivate HTML, you'll have to look into Captivate's Common JavaScript Interface API​ (Also known as cpAPIInterface) in order to have the buttons communicate with Captivate.

If you add the buttons directly to Unity, you'll have to make calls to Application.ExternalCall() inside of Unity in order to call external javascript from your Unity interactive. These calls, presumably, would wind up going through the cpAPIInterface as well. Additionally, you might have to use the javascript function SendMessage() that comes with every WebGL build to call functions on Unity GameObjects from external JavaScript.

In my opinion, I think it would be easier to add the buttons to Unity (although I'm not entirely sure what the functionality of these buttons is). My reasoning for this is simply that it would be easier to lay the buttons out properly using Unity's UI tools than trying to make it work in the iframe or in Captivate's HTML (and the buttons would scale properly with Unity this way as well).

This can be a huge pain, but might be your only hope. If you're going to attempt this, I would strongly advise that you familiarize yourself with the cpAPIInterface, particularly with the getVariableValue and setVariableValue functions, as well as with some of the cpAPIInterface events like CPAPI_SLIDEENTER and CPAPI_VARIABLEVALUECHANGED. Those were the ones I found most useful.

I hope this helps. Best of luck!