Application Development

Add JavaScript Your Way, Part 2

Choose the best option for adding JavaScript to your APEX applications.

By Dan McGhan

December 20, 2019

In part 1 of this article, I showed you how to add JavaScript to APEX applications, using declarative dynamic actions. In this article, I’ll walk you through several more options for adding JavaScript to APEX apps, including dynamic actions with JavaScript hooks, page- and component-level attributes, and application files. Think of these options as a progression, with each one requiring more knowledge of JavaScript, APEX’s JavaScript APIs, and web development in general. New APEX developers should start by learning dynamic actions and progress to subsequent options only when they are ready and the application requirements cannot be satisfied without a more advanced approach.

Dynamic Actions with JavaScript Hooks

Several JavaScript-based hooks are built in to the dynamic action framework to maximize its power and flexibility. These hooks require more JavaScript knowledge to use than the declarative options provided by dynamic actions, but they are a great alternative to writing raw JavaScript code when the declarative options are insufficient.

For example, in the When section of a dynamic action, there’s an Event setting that specifies which browser event to listen for. Although there are many events available to choose from, some uncommon events are not listed, to avoid clutter. What if you need to work with one of the missing events or a custom event emitted by a library you’re using? In either case, the workaround is simple: Use the Custom option.

When you select the Custom option for Event, a Custom Event field is displayed where you can enter any event name you’d like. If you’d like to work with multiple events, separate the event names with a space.

The Selection Type field, just below the event fields, is used to relate the event to an APEX component. If, for any reason, you need more flexibility than the standard Item(s), Button, Region, or Column(s) options, you can choose either jQuery Selector or JavaScript Expression. You’ll find similar options in many actions that affect APEX components.

In the example below, I’m using the Custom event option and specifying two events, one of which is a custom event. I’m also using a jQuery Selector to select all inputs on the page that have a type attribute equal to text.

In the Client-side Condition section, there’s a Type field with various options that compare the value of a single item with a static value. What if you needed to check the value of multiple items or compare the value of an item against a dynamic value elsewhere on the page? Again, the solution is simple: Select the JavaScript expression option. With this option, you can enter any JavaScript expression you’d like. If you need more than a simple expression, you can utilize page-level attributes (covered next) to add a JavaScript function to the page and then call the function from the expression.

Here’s an example where the condition checks to ensure that two different items are null.

Finally, there’s a very flexible type of action that can be used to do anything possible with JavaScript: Execute JavaScript Code. In the following example, I’m using jQuery’s fadeout method to fade out the Alternate Number field on the page instead of just disabling it.

Rather than hard-code the item’s name in the JavaScript code, APEX passes the name in via the Affected Elements section, so that if the name of the item is changed, APEX can propagate the change here too. jQuery’s closest method traverses up to the item’s wrapper to ensure that the label is hidden, along with the actual input field.

As you can see, the JavaScript hooks make the dynamic action framework very flexible.

Page- and Component-Level Attributes

In addition to dynamic actions, APEX includes various page- and region-level attributes meant for raw JavaScript code. Using these attributes requires a bit more comfort with JavaScript, because you’ll need to know how to write functions and, depending on what you want to do, you may need to know more about the Document Object Model (DOM), Ajax, APEX’s JavaScript APIs, and so on. I’ll show you the page-level attributes first and the component-level attributes afterward.

If you go to the page-level attributes and scroll down, you’ll come to a section dedicated to JavaScript. These attributes provide a consistent location where you can put JavaScript code related to an APEX application page.

The two attributes I want to discuss here are Function and Global Variable Declaration and Execute when Page Loads. I’ll touch on the File URLs attribute in the last part of this article.

JavaScript code added to the Function and Global Variable Declaration attribute is executed in the global scope, and it’s run before the DOM load event and before any APEX components are initialized. As its name suggests, this is meant to serve as a place for you to declare any functions and variables that you want in the global scope.

Execute when Page Loads, on the other hand, is meant for code that runs after the DOM load event and after all APEX components have been initialized. Code here will run in a function scope, so variables declared with var will not leak into the global scope.

Here’s an example of how to use these attributes to declare a function and execute it when the page loads:

Because I’m not accessing the DOM and don’t need to access doSomething elsewhere, I could have put all the code in either attribute and it would have worked just fine. But remember earlier when I mentioned that you could use a function defined in the page-level attributes in the JavaScript Expression attribute of a dynamic action’s Client-side Condition? In that case, you would want to put the function definition in the Function and Global Variable Declaration attribute.

If, on the other hand, you want to modify an APEX component, using one of APEX’s JavaScript APIs, you’ll want to wait until the DOM is loaded and the APEX components are initialized. For that, you would need to put the function code (or at least the code that invokes the function) in the Execute when Page Loads attribute.

As of APEX 19.2, the following APEX components include a JavaScript Initialization Code attribute:

  • Regions
    • Interactive Grid (region and column level)
    • Chart
    • Calendar
    • Tree
  • Items
    • Rich Text Editor
    • Markdown Editor (19.2+)
    • Popup LOV (19.2+)

The JavaScript Initialization Code attribute uses the same pattern for each component. You define a function that accepts an options object that will contain any relevant default options. In the body of the function, you modify any supported options and return the options object. APEX will invoke the function while initializing the component and use the options you’ve specified.

The help for this attribute varies for each component and provides an example to get you started. Here’s an example from a chart region:

The example code above is changing the color of a series and setting the chart type to a line chart. You’ll need to consult the documentation to learn about the available options. For a component such as Interactive Grid, you’ll find the options documented in the APEX JavaScript API documentation. However, in the case of chart regions (which are now based on Oracle JavaScript Extension Toolkit [Oracle JET] charts), you’ll need to consult the JET documentation.

External Files

If you find that you’re working with a lot of raw JavaScript or you have JavaScript that you’d like to share across multiple APEX application pages, you’ll want to start leveraging external files. External files can be cached by the browser and are easily shared across multiple pages in an application—and, as you’d expect, APEX makes it very easy to use them.

I’ll show you how to move the doSomething function shown before in a page-level attribute to an external file. First, create a new JavaScript file and add the code there. I’ve named my file my-js-code.js.

Next, navigate to Shared Components -> Static Application Files. Click Upload File >, and use the dialog box to upload the file. When the file is uploaded, you should see it displayed in Static Application Files.

Note the Reference column, which contains a URL you can use to add the file to different parts of the application. Copy that value, and navigate to the page where you’d like to use the file. Locate the File URLs attribute in the JavaScript section of the page-level attributes, and paste the URL value there. You can clear the value in the Function and Global Variable Declaration attribute, because the code will now come from the JavaScript file.

If you run the application page, you’ll see that the code works just as before. It’s quite easy to add the file reference to multiple pages if you’d like to share it. In the event you’d like to add the JavaScript file to all pages in the application, navigate to Shared Components -> User Interface Attributes; select the appropriate user interface, such as desktop; and add the file reference to the File URLs attribute in the JavaScript section.

Hopefully you’ll agree that APEX provides robust support for adding JavaScript to your APEX applications. If you’d like to learn more about this topic, consult the JavaScript API documentation. Happy JavaScripting!

Next Steps

LEARN more about JavaScript and Oracle.

TRY Oracle Cloud Free Tier.

READ Add JavaScript Your Way, Part 1.

Illustration by Wes Rowell