By now some of you heard that Oracle is planning to include Oracle JET charts in Apex 5.1. The scope of this article is to show you how it is possible to use Oracle JET features already in Apex 5.0.3.

It is generally easy to use 3rd party JavaScript libraries with Apex, but there are quite a few traps and surprises when trying integrate JET in Apex. What makes using Oracle JET with Apex tricky is that JET requires you to use RequireJS to load needed JavaScript libraries dynamically.

Download Sources

In order to install Oracle JET, we first need to download the newest version. To do so download oraclejet.zip files under the “Oracle JavaScript Extension Toolkit : Base Distribution” from the following page.

Download Link : http://www.oracle.com/technetwork/developer-tools/jet/downloads/index.html

Server Installation Process

Now we need to have access to the Apex web server to paste in Oracle JET files so that we can reference the needed JS and CSS files in Apex page later. I suggest to put them in apex/images/libraries folder because apex/images is typically mapped as the image path /i/ and we can later use the substitution variable #IMAGE_PREFIX# .
For example let’s say we want to include the ojs.js file, to do so we reference it like this : #IMAGE_PREFIX#libraries/oraclejet/libs/oj/v2.0.0/ojs.js

Unzipping the file into some accessible folder is all we need for the server installation part.

Integrating Oracle JET into Apex Universal Theme

 

As I said before the tricky part about making those two to work together is that Oracle JET forces us to use require.js if you plan to use Oracle JET’s internationalization or data visualization components in your application. Most of the problems I have encountered had to do with require.js.

How is this a problem?

Well the traditional way of using JavaScript libraries on a web page is to include them with the help of script tags. Each script file adds some global symbols for other libraries to use. This is how Apex does it.

Oracle JET uses modules as a way to keep code, modular and explicitly define what your module exports and what dependencies you have in other modules. All needed is a script tag and a module system, RequireJS, which provides a mechanism for asynchronously loading a module and its dependencies.

The problem appears when the existing non-module code and the new module code wants to share the same library.
So let’s try integrate the ojswitch button from Oracle JET into Universal Theme
to better see where the problem is and how to work around it.

The Oracle JET documentation tells us how to install RequireJS.

The loader that makes it easier to manage library references and is designed to improve the speed and quality of your code. Oracle JET uses RequireJS by default for the Oracle JET – QuickStart Template and is required if you plan to use Oracle JET’s internationalization, data visualization components, or the oj.OAuth plugin in your application.

To use RequireJS to manage references:

  1. Download Oracle JET as described in download the Oracle JET Zip File.
  2. Copy js/libs/oj/version/main-template.js to the js
  3. In the js folder, rename main-template.js to js.
  4. Add the following script reference to your html file:
  <script data-main="js/main" src="js/libs/require/require.js"></script>
  1. Update JS as needed to reference Oracle JET modules or your own scripts.

For a list of Oracle JET modules and additional details about using RequireJS in your  application see Using RequireJS for Modular Development.

So in the documentation from Oracle they say that we need to use a main.js file to reference modules. We are not going to use a main.js file to do this because if we further want to add another Oracle JET feature we will need to download this file, modify it in order to include the needed modules for the additional feature and upload it back again, instead we are going to copy/paste the code from main.js directly into the page template that uses Oracle JET components.

Let’s start, so in order to include Oracle JET CSS and JS files we need to reference them in the universal theme, unfortunately the only way that we can do this is by unsubscribing the theme. After unsubscribing, we can edit the Theme as we want.

To do so login into your Apex workspace, go to Application Builder select the application into which you want to integrate Oracle JET features.
Now go to Shared Components.

SharedComponents

Next under User Interface go to Themes.
SharedComponentsThemes

Next click on the Universal Theme to edit it.

UniversalThemeSelect
Now under Theme Subscription tab click on Unsubscribe.
ThemeSubscription

Now you can edit the Universal Theme as you wish.
Now let’s include RequireJS and CSS files needed to use Oracle JET features.

To do that we need to edit the universal theme to reference them.

Go to JavaScript and Cascading Style Sheets tab. Here in the JavaScript File URLs box include require.js file like bellow:

#IMAGE_PREFIX#libraries/oraclejet/js/libs/require/require.js

RefernceRequireJSIntoUV

And in the CSS File URLs box include oj-alta-min.css file like bellow:

#IMAGE_PREFIX#libraries/oraclejet/css/libs/oj/v2.0.0/alta/oj-alta-min.css
ReferenceJetCSSIntoUV

Now let’s check if the libraries are loaded successfully or if we get any errors.


Run the application then on Firefox open the console (CTRL+SHIFT+K) and switch to Network and also click on JS tab in order to see if there are any JavaScript errors.

OracleJetApexError

As you can see in the above screenshot the libraries were loaded successfully but we get an error: Mismatched anonymous define() module  coming from require.js .

Here we encounter the problem we talked about in the beginning, that Apex (non-module) and RequireJS (module) wants to include the same library, in this case hammer.js.

If the hammer.js script tag is loaded after require.js it defines an anonymous module then as soon as you do anything else with RequireJS you get the error presented above.

 The reason why this happens is because RequireJS insists that all anonymous modules are loaded from a define or require call.

Now a solution could be to load the hammer.js before we include require.js. This will do it, you will get rid of the error but then in the future if you will want to use an Oracle JET component that uses hammer.js you will have duplicate code and I suggest to avoid doing this.

SOLUTION

Well, what I suggest to do is to remove hammer.js from JavaScript File URLs box and load it using RequireJS from a require call.

ReferenceRequireJsWithoutErrors

Ok, so let’s do so.

After you’ve removed the hammer.js library we can integrate an Oracle JET component into apex.

Further I’m going to create an ojswitch button to include in our Apex homepage.

Link : http://www.oracle.com/webfolder/technetwork/jet/uiComponents-switch-switchcomponent.html

First we create a template for our button and add the html from the cookbook.

1. To do so got Shared Components and under User Interface click on Templates.
SharedComponentsTemplates

2. Click on Create.

CreateApexTemplate
3. Select as Template Type Button and click

ApexButtonTemplate

 

4. As Creation Method select From Scratch.
CreationMethodApexButtonTemplate

5.
Now give it a Name, Universal Theme as Theme and a Theme Class.

SetApexButtonTempalteName

Hit Create and we are done with creating the template.

Now we need to add to it the html from the cookbook.

To do so you need to edit the template same way as you edited the theme.
Here under the Definition tab in the Normal Template box we add the html from the cookbook and save it by clicking on Apply Changes like so.

DefineApexButtonTemplate

Now we have to add JavaScript functions from the cookbook to the page itself (global functions section).
Next we need to add the require call including the configuration part in the JavaScript section of the page from that main.js file. On each page where we want to add some JS files from Oracle JET we would do a require call immediately before the relevant section.

So we need to go to the folder where you unzipped Oracle JET and then copy the code inside main-template.js which is located at : js/libs/oj/version/main-template.js and modify it like you see below.

To enable ojSwitch we need to require ‘ojs/ojswitch’ and also include hammer.js.

require.config({
  baseUrl: '#IMAGE_PREFIX#libraries/oraclejet/js',
  paths: {
    'knockout': 'libs/knockout/knockout-3.4.0',
    'jquery': 'libs/jquery/jquery-2.1.3.min',
    'jqueryui-amd': 'libs/jquery/jqueryui-amd-1.11.4.min',
    'ojs': 'libs/oj/v2.0.0/min',
    'ojL10n': 'libs/oj/v2.0.0/ojL10n',
    'ojtranslations': 'libs/oj/v2.0.0/resources',
    'signals': 'libs/js-signals/signals.min',
    'text': 'libs/require/text',
    'promise': 'libs/es6-promise/promise-1.0.0.min',
    'hammerjs': 'libs/hammer/hammer-2.0.4.min',
    'ojdnd': 'libs/dnd-polyfill/dnd-polyfill-1.0.0.min'
  },
   // waitSeconds: 1,
  // Shim configurations for modules that do not expose AMD
  shim: {
    'jquery': {
      exports: ['jQuery', '$']
    }
  }
});      
 
require(['ojs/ojcore', 'knockout', 'jquery', 'ojs/ojknockout', 'ojs/ojswitch','hammerjs'], 
function (oj, ko, $) {
function SwitchModel(){
        this.isChecked = ko.observable();
    }

    var switchModel = new SwitchModel();
 
    $(document).ready(
        function()
        {
            ko.applyBindings(switchModel, 
                document.getElementById('formId'));
        }
    );
  });

 

Now all we need to do is add this JavaScript code to the page that will use the ojswitch component.

To do so, go to Page Designer and under Rendering tab in the left select Page.
Then in the right column under Page Properties go to Appearance -> Page Template and click on Go To Page Template ( > )button like bellow :
GoToPageTemplate

Next click on Edit Component.

EditApexPageTemplate

Next we are redirected to Edit the Page Template in Shared Components. Here go to JavaScript tab and add the code above in the Function and Global Variable Declaration box like so:

AddJSForOjSwitchComponent
Click Apply Changes to save the template.

Now we are done, so let’s add the ojswitch button to the Home Page which we configured for Oracle JET and see if it’s working.

Go to Page Designer to edit the Home Page and under buttons you should see our newly created OjSwitchTemplate button . Now drag and drop it into the page like below:
AddOracleJetComponentToApexPage
Now we are done. Let’s Run the page and see if it works.

RunApexPage

Success! Now we can see the Oracle JET switch button is working like in the pictures below.

OjSwitch OFF

oracleJetOjSwitchOff

OjSwitch ON

oracleJetOjSwitchOn