Introduction
In a previous post, APEX Dynamic Inline Help, I showed you how to create dynamic in-line help text. In this post, I will describe an approach for providing help text (sourced from outside of APEX Builder) to display when the❓icon is clicked.
Why do we need Custom Help Text?
Two customers recently asked me if APEX allows you to source help text from a source outside of APEX Builder. The driver for this is that they want their end users to be able to manage help text in a separate APEX Application. Standard APEX help text must be entered in APEX Builder. This, together with the fact that there is currently no PL/SQL API to maintain APEX help text, rules standard APEX help out.
This means we need some way to intercept the standard help text and call some PL/SQL code to get the help from our own help text table.
Standard Page Item Help
Let's level set by understanding how out-of-the-box help works for APEX Page Items. To enable standard APEX Page Item help, you only need to enter some help text in the 'Help Text' item property.
After entering the help text, a❓icon appears to the right of a page item.
Clicking the icon then shows the help text you entered in APEX Builder.
Implementing Custom Help
Overview
My approach involves the following three steps:
Design an Alternate Help text table.
Display the❓icon for page items that require help.
Intercept the standard event that fires when you click the❓icon, fetch our own help, and display it to the end user.
1 - Alternate Help Text Table
Let's start by creating a table to store our alternate help text. I have created a table called CUSTOM_APEX_HELP_TEXT
, with the following columns:
There is a unique index on HELP_KEY
and LANGUAGE_CODE
.
2 - Displaying the❓Icon
This part is easy; APEX already displays the help icon when you enter text in the 'Help Text' item property. The difference is that instead of entering the help text, we will enter a token or key that matches the HELP_KEY
column in our table.
This is what the end user sees:
3 - Detect Click on❓and Display Custom Help
For this step, we will create a Dynamic Action that fires whenever the user clicks on the❓icon. On page 0, create a Click
Dynamic Action that fires when the .js-itemHelp
class is clicked.
Let's pause here and show you how I knew to choose the
.js-itemHelp
class and how I knew that thedata-itemhelp
attribute stored the APEX Page Item ID. I discovered this by inspecting the HTML for the❓icon displayed to the right of a page item. The applicable attributes are highlighted in green in the screenshot below.
The Dynamic Action calls a JavaScript function called cnHelpUtil.showHelp
:
The JavaScript function is created in a Static Application file and has the following code:
/**
* @namespace var cnHelpUtil = {};
**/
var cnHelpUtil = {};
/**
* @function showHelp
* @example cnHelpUtil.showHelp(this, 'ITEM');
**/
cnHelpUtil.showHelp = function (theEvent, helpTrigger) {
// Stop the standard help functionality from running.
theEvent.browserEvent.stopImmediatePropagation();
let helpValue;
// Determine if trigger was a Page Item or an IG/IR Column.
if (helpTrigger == 'ITEM') {
// For an APEX Page Item we can get the Item ID from the Attribute 'data-itemhelp'.
helpValue = $(theEvent.triggeringElement).attr('data-itemhelp');
} else {
// For an IG or IR column we have provided the attribute 'cn-help-key' along with the help key.
helpValue = $(theEvent.triggeringElement).attr('cn-help-key');
}
apex.debug.info("Trigger ", helpTrigger);
apex.debug.info("Source ", helpValue);
// Call an APEX Server Process to Fetch the Help Text.
apex.server.process('FETCH_CUSTOM_HELP',
{x01: helpTrigger,
x02: helpValue},
{success: function (pData) {
// Display the Help Text.
apex.theme.popupFieldHelp({title:'Item Help', helpText: pData.help_text});
},
error: function(e){
console.log(e);
apex.message.clearErrors();
apex.message.showErrors([
{
type: "error",
location: "page",
message: 'Unable to get get Custom Help',
unsafe: false
}
]);
},
dataType: "json"
}
);
}
The JavaScript function performs the following steps:
Determine if the user clicked the❓icon from an APEX Page Item or an Interactive Grid or Interactive Report column. More on IG/IR Column help later in this post.
Determine the
help_key
based on where the❓icon was clicked.Call an Application Server Process
FETCH_CUSTOM_HELP
to fetch the help text.Display the help text to the user.
The result looks and behaves exactly like the standard APEX help, except you can get the help text from anywhere.
The APEX Server Process called from the JavaScript function (FETCH_CUSTOM_HELP
) is declared under Shared Components > Application Processes as follows:
Here is the source code for the package CN_CUSTOM_HELP
:
Other APEX Help
Of course, there are other areas where you can add help to your APEX Applications. This section will describe these areas and options for sourcing your own help text.
Page Help
Page help is the easiest area to utilize your own help text. Out of the box, you can easily create a help page and region by following these instructions. This approach automatically sources help text from the 'Help' page property in APEX Builder.
You can easily change the help page created by the above instructions to fetch help text from your own source.
Interactive Grid Column
When you add help text to the Interactive grid column attribute 'Help Text', APEX will show an additional column in the Column toolbar where a user can access the help text.
I have spent some time looking into the code behind the IG Column toolbar and could not figure out an elegant way to inject my own code so that I could source my own help text. My less-than-elegant solution is to add a <span>
to the IG column heading. This adds a❓icon to the right of the column heading and includes a data attribute that I can use to specify the help key to use when the user clicks the❓icon.
This is what it looks like to the end user:
This is what it looks like in APEX Builder. In this example, I have set the cn-help-key
data attribute equal to COUNTY
.
County<span class="fa fa-question-circle-o padding-left-sm"
cn-help-key="COUNTY" aria-hidden="true"></span>
I created a second Dynamic Action on Page 0 that responds to a user clicking on the attribute cn-help-key
:
The Dynamic Action calls the same cnHelpUtil.showHelp
JavaScript function we used for APEX Page Item Help above. The only difference is that we pass the parameter 'IG_IR' to tell the function we call from an IG or IR Column.
Interactive Report Column
Like an Interactive Grid, when you add help text to the column attribute 'Help Text', APEX will show❓icon in the column toolbar where a user can access the help text.
To add our own help, we can use the same approach for Interactive Report Columns as for Interactive Grid Columns. We must add the same <span>
to the IR column heading. The same Page 0 Dynamic Action we used for Interactive Grid columns will also detect the click of the❓icon on the IR column and call the JavaScript function cnHelpUtil.showHelp
to fetch the help text for the help key and display it to the end user.
Conclusion
Ideally, APEX Builder would provide a property where you could provide a PL/SQL function for APEX to call when the user clicks the standard❓icon. This would apply to Page help, Page Item help, and IR & IG Column help.
Whenever a user clicks the❓icon, APEX calls the custom PL/SQL function, passing the current page item, the current session language, and a key/identifier you provide. Your PL/SQL function code could then source the help text from anywhere you want.