Showing posts with label Fluid Branding. Show all posts
Showing posts with label Fluid Branding. Show all posts

Tuesday, March 19, 2019

JavaScript Injection Framework - Updates, Bugs and Fixes

The reason I am writing this blog post is to make readers aware of the latest version of the JavaScript Injection Framework and known bugs/fixes associated with the older versions.

If you read some of my previous posts on Branding and other UI enhancements, you may have come across several attempts made by me to find a means to globally (system wide) inject JavaScript/CSS. Unfortunately, there is no way to do this via delivered configuration/code so I ended up writing custom javascript code.

Over the years, I have made iterative improvements to this code and created a framework of sorts with a minimally invasive customization.

Early (Beta) version
https://pe0ples0ft.blogspot.com/2015/11/peopletools-854-branding-part-5b-fluid.html#FluJSInjectionBootstrap

Updated version (using RequireJS)
https://pe0ples0ft.blogspot.com/p/javascript-injection-framework.html

As I was making further changes, I moved this framework to GitHub in an effort to better manage the code/versioning.

GitHub Project
https://github.com/SasankVemana/PeopleTools-JavaScript-Injection-Framework

Recently, the following Doc ID was brought to my attention via a twitter post.

Oracle Support Document 2294106.1
E-PIA: Run to HTML,Excel and XML links in Query Manager and Query Viewer spinning for ever while running a report having prompt criteria

Twitter Thread
https://twitter.com/ArcherHuck/status/1085635936053051394
After reviewing Doc ID 2294106.1, I realized that this issue is most likely caused by a customer who implemented this JavaScript Injection Framework. The issue reported in the Doc ID, is very similar to an existing issue identified with an older version of the framework.

Reported Issue: https://pe0ples0ft.blogspot.com/p/javascript-injection-framework.html#c6317103235239955618

The solution provided by Oracle in the Doc ID is to completely remove the custom framework which is understandable since this is not Oracle code. But this issue can be overcome by using the latest version of the JavaScript Injection Framework. In the latest version of the bootstrap javascript as shown below, the regex pattern is updated to account for an extended list of PeopleSoft URL types.


Additionally, the latest version of the framework that is available on GitHub also addresses and fixes some race conditions (which I ran into under certain circumstances) associated with RequireJS and other custom scripts.

Here are some resources that are very useful to understand common timing issues related to javascript functions and callbacks.

https://blog.kevinchisholm.com/functions-javascript/javascript-callback-functions-the-absolute-basics/
https://www.sitepoint.com/understanding-requirejs-for-effective-javascript-module-loading/

Wednesday, April 25, 2018

Adding Custom Links to Action Menu using DoURLWarning JavaScript Function

In the past, I wrote about how we can add custom links to the Branding - Action Menu at the system level.

Refer: Adding Custom Links to Fluid Branding

While testing this feature, I found that these custom links do not work in certain scenarios. For example, clicking those links from within the NUI Activity Guide framework (which is also used in Nav Collections).


I originally used the FieldChange event and the Response Class RedirectURL method to implement the redirection logic in Fluid Branding as shown below.


Since the Response Class RedirectURL method proved to be problematic in certain scenarios, I started investigating other options. In the process, I found this great delivered JavaScript function called DoURLWarning which is part of PT_HISTORY object in 8.55+ (PT_PAGESCRIPT_FMODE object in 8.54).


DoURLWarning function allows us to redirect to a URL using javascript. Additionally, the function will take care of checking for any unsaved data in the current page and if there is any it will display the "Save Warning" message. If not, it will redirect to the URL in the parameter list.

To use the DoURLWarning function, I removed all the redirect logic from the FieldChange Event. And added code in the RowInit event (as shown below) to utilize the DoURLWarning in combination with the Field Class JavaScriptEvents Property.


PeopleCode for reference

Demo

As we can see in the demo video, the custom link on the Action Menu works when invoked from the Activity Guide framework (which is also used in Nav Collections). The same approach described above can be used to implement custom links to internal PeopleSoft pages as well (e.g.: Process Monitor, Report Manager, etc.).


Save Warning Demo


Fluid UI New Window Feature Implementation

I used a similar technique as described above to implement the 'New Window' feature in Fluid UI as a custom link on the Branding - Action Menu.

Refer: Fluid UI - New Window Feature - Workaround

The only difference in the implementation is that instead of using the Response Class RedirectURL method (which would redirect/replace within the current window), I used the ViewContentURL method to open a new window as shown below.


We can see in the demonstration below, that the same problem described for the custom links also exists for this New Window implementation.


To workaround the problem, I took a similar approach and removed the existing logic from the FieldChange event and moved it to the RowInit event. In the RowInit event, I used the Field Class JavaScriptEvents Property in combination with the Window interface's open method as shown below. Additionally, I also updated the logic to include the %Request.QueryString to the URL to make sure that none of the additonal parameters are lost when opening the new window.


PeopleCode for reference

Demo


Sunday, January 29, 2017

Fluid UI - New Window Feature - Workaround

Graham Smith created an idea on My Oracle Support Community to carry forward the "New Window" feature in Fluid pages especially for users on the desktop (or non-small form factor devices).

We can understand that Fluid user interface is designed with a mobile first and more importantly small form factor (SFF) first approach. This is one of the reasons why we don't get the Toolbar Actions (Save, Return to List, Next in list, Previous in list, etc.) by default on Fluid pages. But Graham has rightly pointed out that Fluid is not just an UI for mobile devices, we also need to account for users on desktops who are accustomed to opening new windows using the "New Window" feature.

This idea is trending and has already received several votes in a short period. I am hoping this would be incorporated as an enhancement in the future PeopleTools releases. I encourage everyone to continue voting. The more the merrier!
https://community.oracle.com/ideas/16701
 
Workaround while we wait?

Note: The workaround suggested in this post involves a minor customization. As with any customization, we will need to determine - based on our environment and circumstances - if the cost of maintaining this customization (until such time as we receive a solution from Oracle) outweighs the benefits!

Let us say that we decided to go down the path of introducing the "New Window" feature in Fluid, where would we put it? I am not convinced that bringing it back in literal terms and placing it exactly where it was located in Classic pages would be a good fit for Fluid (even if we are only talking medium, large and extra large form factors). If we notice, the traditional "Help" feature that links to context sensitive PeopleBooks, is now located in the Action Menu on the Fluid Header.

New Window and Help links in Classic:


Help link in Fluid:


It seems logical to similarly add the "New Window" functionality to the Action Menu in the Fluid Branding Header! That way, we will not be interfering with the content area of the page.

In my previous posts on Branding, I described how we can globally (across the application) add a link to the Action Menu in the Fluid Branding Header. I demonstrated the concept using an external link as an example.
Refer: Adding Custom Links to Fluid Branding

We can follow the same steps to add the 'New Window' link as well. In my case, I already created the custom subpage (CSK_HEADER_ACTION). I simply added a groupbox and a hyperlink (derived work field) to the subpage (similar to the external link example).



I added the following PeopleCode on the FieldChange event to open a New Window.


Updated on 04/26/2018

Please refer the below blog post for updated code/logic.
https://pe0ples0ft.blogspot.com/2018/04/adding-custom-links-to-action-menu.html#2

Results:



Suppress New Window feature on Small Form Factor (SFF) Devices (Optional):

If we would like to suppress the New Window feature for SFF devices, then we can simply configure this using the page field properties as shown in the following screenshots.



PeopleCode for Reference:

&fullURI = %Request.FullURI;

&pos1 = Find("/psc/", &fullURI);
&part1 = Substring(&fullURI, 1, &pos1 + 4);
&part2 = Substring(&fullURI, &pos1 + 5, Len(&fullURI));

&pos2 = Find("/", &part2);
&part3 = Substring(&part2, 1, &pos2 - 1);
&part4 = Substring(&part2, &pos2, Len(&part2));

&pos3 = Find("_", &part3);
If &pos3 = 0 Then
   &site = &part3;
Else
   &site = Substring(&part3, 1, &pos3 - 1);
End-If;

&newWinURL = &part1 | &site | "_newwin" | &part4;
ViewContentURL(&newWinURL);


Related Posts - Productivity Enhancements:
Fluid UI - CTRL+J - On Mobile Devices

Sunday, June 12, 2016

PeopleTools 8.55+ - Using Oracle JET (JQuery, JQueryUI, requireJS and more) - Part 4

This post is a continuation of my 'PeopleTools 8.55+ - Using Oracle JET' series (refer: Part 1, Part 2 and Part 3).

In Part 1 (refer: Global JavaScript Injection Bootstrap for Fluid UI - Step 3), I pointed out that using 'Branding System Options' for injecting javascript in Classic pages would result in them getting invoked more than once (per header, pagelet, target frame, etc.). For most Branding Tasks, this might not be necessary since we are only dealing with the header portion of the HTML and other general styling.

All the topics described so far in this series worked fine with the 'Global JavaScript Injection Bootstrap' getting invoked just once as detailed in Step 2 and Step 3. But there may be some advanced requirements possibly outside the scope of Branding where we may intend to inject the Global JavaScript once per header, pagelet, target frame, etc. in order to manipulate the target content area, form data/component buffer and so on. For such cases (to be detailed in a subsequent post), we could use the following alternative step to include our 'Global JavaScript Injection' Bootstrap JS.

Note: The following step would replace Step 2 and Step 3 (which means we need to revert both those changes).

Add CSK_FL_BOOTSTRAP_JS to Classic and Fluid using PT_UTIL JS object:

PT_UTIL is a delivered javascript object that is included in Fluid (via PT_COMMON_FMODE) and Classic (via PT_COMMON). My thought was to simply include our custom bootstrap javascript object in PT_UTIL (using the %include meta-html).


Additionally, I updated the javascript CSK_FL_DBNAME_JS as follows:

Object Name: CSK_FL_DBNAME_JS


The only change was the window.self == window.top condition to avoid the following 'custom header repetition' problem.


The rest of the javascript objects detailed so far in this series should work as-is without any issues.

Monday, May 30, 2016

PeopleTools 8.55+ - Using Oracle JET (JQuery, JQueryUI, requireJS and more) - Part 3

This post is a continuation of PeopleTools 8.55+ - Using Oracle JET to leverage open-source libraries such as JQuery, JQueryUI, requireJS, etc. - Part 1 and Part 2.

In Part 1, I described how to create a JavaScript Injection Bootstrap framework particularly useful for Fluid UI since the Branding System Options only work for Classic. Similarly, let us assume we want to add custom styles to Fluid UI. How do we achieve something like that? We could use the 'Global Override Style Sheet' (CSK_BRAND_FLUID_TEMPLATE) which is part of our custom theme (CSK_THEME_FLUID). This would work just fine if we are either overriding a existing delivered Fluid style class or if we are adding some additional custom styles to the 'Global Override Style Sheet'. But what if we want to load entire style sheets from open source libraries such as JQueryUI? What if we want a configuration that allows us to inject style sheets globally as and when new requirements come up? Wouldn't it be great to have a global style sheet injection framework similar to the 'JavaScript Injection Bootstrap' from Part 1?

Global Style Sheet Injection:

I added a couple of javascript functions to my existing bootstrap javascript object (CSK_FL_BOOTSTRAP_JS).

JavaScript Functions: getCSSUrl(cssId) and cskLoadCSS(path)



As the names suggest, getCSSUrl uses the delivered IScript_GET_CSS to return the URL of a CSS object on the web server cache directory and cskLoadCSS would inject the CSS with a specified source path to the DOM.

CSK_FL_BOOTSTRAP_JS:


Now, we should be able to use the function cskLoadCSS and getCSSURL, (e.g.: cskLoadCSS(getCSSUrl('PSJQUERY_BASE_1_8_17'));...) from any javascript (e.g.: CSK_FL_BOOTSTRAP_JS), to inject style sheets globally across the application. I will demonstrate this in a use case as part of the next section.

Fluid UI - Control + J Alternative using JQuery, JQueryUI and requireJS:

In Part 1 and 2, although we used requireJS as part of Oracle JET, we only employed it for a simple use case of loading the JQuery library. In this section, I will demonstrate how we can use requireJS for a more complex requirement where we will need to load more than one version of the JQuery library along with JQueryUI. This use case is to create an alternative and a device agnostic approach for surfacing the Control + J information to the end users in Fluid UI (click here for more details).

As I mentioned previously, my requireJS configuration was very basic and derived from a delivered example for the purposes of Part I and Part 2. In this section, I will update my requireJS configuration (CSK_REQUIRE_CFG_JS) based on requireJS documentation.

Update JavaScript Object: CSK_REQUIRE_CFG_JS



You can see that I have added the two versions of JQuery to the path mapping as jquery for version 2.1.3 (part of Oracle JET) and jquery_1_7_2 for version 1.7.2 (stored as a custom javascript object CSK_JQUERY_1_7_2_JS and added via Branding Objects). I also added jqueryUI version 1.11.4 which is available as a delivered object - PT_JQUERY_1_X_JS. Lastly, jquery-private takes care of mapping modules to use NoConflict (click here for more details).

Note: The javascripts CSK_FL_DBNAME_JS and CSK_OVERRIDE_IMAGE_JS created in Part 1 and 2 will continue to work with the update version of CSK_REQUIRE_CFG_JS.

Next, I created an updated version of my CSK_FL_CTRL_J_JS javascript object.

JavaScript Object: CSK_FL_CTRL_J_JS



The main difference is that I am using requireJS to load jquery_1_7_2 and jqueryui as dependencies for this javascript. Also, notice that I am using cskLoadCSS function to inject the style sheet PSJQUERY_BASE_1_8_17 (delivered object that contains jQuery UI CSS Framework 1.8.17) and CSK_CONTROL_J_CSS (custom style sheet to manage some quirks with Control + J - JQueryUI Dialog styling).

Style Sheet Object: CSK_CONTROL_J_CSS



Why do we need CSK_CONTROL_J_CSS?

To handle quirks with JQueryUI styling due to using different versions of JQueryUI and JQueryUI CSS.

Quirk 1:


Quirk 2:


Load Fluid Control + J JavaScript (CSK_FL_CTRL_J_JS) using the Fluid JavaScript Injection Bootstrap:

Simply add CSK_FL_CTRL_JS to the cskInjectJS function in CSK_FL_BOOTSTRAP_JS object.


Results:

To invoke the "Troubleshooting Information" dialog, all we have to do is to press the mouse (PC/Mac) or touch the screen (mobile devices) - anywhere on the webpage - continuously for 5 seconds!



Sunday, May 29, 2016

PeopleTools 8.55+ - Using Oracle JET (JQuery, JQueryUI, requireJS and more) - Part 2

In my recent post (click here), I detailed how we could use Oracle JET to safely and efficiently take advantage of some the common open source libraries such as JQuery, JQueryUI, requireJS, etc. I also created a cleaner version of my JavaScript Injection Bootstrap and used it to inject a custom javascript (which uses JQuery) to add an environment specific header for both Fluid and Classic in PeopleTools 8.55.

In this post, I want to continue with that process and re-write the configurable image replacement technique that I described for PeopleTools 8.54 (click here for more details).

IScript for Image Object Source URL Resolution:
 
Reference to the previous version of the IScript: Click here.

Since using meta-HTML such as %Image and %JavaScript does not work in JavaScript objects, I created my own version of  an IScript which returns the URL referencing an image object on the web server (loaded on the cache directory).

WEBLIB_FL_CSK.ISCRIPT1.FieldFormula - IScript_CSK_GET_IMG


PeopleCode for reference:

Function IScript_CSK_GET_IMG
  
   Local string &img = %Request.GetParameter("img");
  
   &url = %Response.GetImageURL(@("Image." | &img));
   %Response.RedirectURL(&url);
 
End-Function;


Create a custom javascript function and add it to the JavaScript Injection Bootstrap (CSK_FL_BOOTSTRAP_JS):

This function would help us to mask some of the details to access the preceding IScript to get the Image URL (similar to the getScriptURL function which I borrowed from Jim Marion's blog).

Function Name: getImageURL


Let us add this function to the JavaScript Injection Bootstrap:


Configurable JavaScript for Image Replacement (CSK_OVERRIDE_IMAGE_JS):

Object Name: CSK_OVERRIDE_IMAGE_JS



This javascript object CSK_OVERRIDE_IMAGE_JS is a re-write of my previous version which was called CSK_FL_IR_JS. You will notice that I am using requireJS to load the JQuery library that I need for this function execution. I am also using the getImageUrl function which I previously detailed to get the URL of the custom images. These URLs will be used to override the corresponding delivered counterparts. Right now, I have two examples for image replacement: 1) Replace the delivered Favorite Icon with a custom image (CSK_LOGO_FAVICON) and replace the delivered 'Processing' icon for Fluid with a custom image (CSK_PROCESSING_FMODE).

LOGO_FAVICON (delivered):


CSK_LOGO_FAVICON (custom):


PT_PROCESSING_FMODE (delivered):


CSK_PROCESSING_FMODE (custom):


Similarly, we can configure additional image replacements by simply appending code to the CSK_OVERRIDE_IMAGE_JS javascript object.

Load Image Replacement JavaScript using the Fluid JavaScript Injection Bootstrap:

Simply add CSK_OVERRIDE_IMAGE_JS to the cskInjectJS function in CSK_FL_BOOTSTRAP_JS object.


Results:



Friday, May 27, 2016

PeopleTools 8.55+ - Using Oracle JET (JQuery, JQueryUI, requireJS and more) - Part 1

If you followed some of my previous posts related to Fluid Branding, you would have noticed that I complained a fair bit about 8.54 and 8.55 not delivering jQuery by default for Fluid UI. Although, I still think that it is a missing feature in 8.54, I found that Oracle has delivered something better in 8.55. This is not really mentioned in great detail anywhere, but if you look on the web server, you will find that Oracle JET (Oracle JavaScript Extension Toolkit) is available. For those who are not aware, it is like a package of all the commonly used open-source js and css libraries put together. In addition to the open-source libraries, Oracle JET also contains a set of Oracle contributed js libraries.

Web Server:


Oracle JET usage in charts:

I also noticed this in a few Fluid pages containing charts, when I inspected the DOM elements. I have not seen widespread usage in other areas.


If you have read some of my previous Fluid Branding posts (Part 5B and Part 5C) where I described how I created a Fluid JavaScript Injection Bootstrap and few other advanced Branding topics using JavaScript and JQuery, you would notice that I hacked (for lack of a better term) my way through the requirements. I will admit that my js code was probably not the most efficient. In this post and perhaps other follow up posts (Part 2 and Part 3), I plan to revisit some of the javascript and rewrite the logic using Oracle JET (e.g.: Fluid JavaScript Injection Bootstrap and Environment Specific Header for Non-Prod databases).

In the following sections, I intend to cover the topic of using JQuery and JQueryUI libraries safely in conjunction with requireJS - available in Oracle JET on PeopleTools 8.55+ applications. When I say 'safely', I mean to safely manage dependencies using requireJS. Jim Marion has already written about how to achieve this in an 8.54 environment (and probably in several other posts on his blog where he covered the usage in previous tools versions as well).

If you are a fan and a follower of Jim Marion's PeopleSoft Journal blog (like myself) and if you are wondering why he has been relatively quiet (for his standards) in the past few months, he has been blogging all along at a ferocious pace and putting out some great content on Oracle JET in his new blog Jim's JavaScript Journal - tailored for javascript and Oracle JET applicable to all users and not specific to PeopleSoft!!! :)

Global JavaScript Injection Bootstrap for Fluid UI:

My requirements for this bootstrap are still the same as in 8.54. Since there was and still is no way to inject custom javascripts globally in Fluid, I want to create a least intrusive and highly configurable bootstrap to easily inject javascripts on the fly.

Step 1: Create a custom javascript object for the Bootstrap code

Navigation: Navigator > PeopleTools > Portal > Branding > Branding Objects (JavaScript Tab)

Note: This javascript object needs to be added online so that it provides a configuration to inject additional javascript objects.

Object Name: CSK_FL_BOOTSTRAP_JS


- This javascript object might seem a lot lengthier than my previous version but it should be cleaner and a lot more efficient.
- getScriptUrl: I borrowed this function from Jim Marion's post. It provides a nice and clean way to derive the URL for a javascript object.
- cskLoadJS: I improvised this function from the delivered loadScript function (PT_CHART_LOAD). It helps with adding a javascript (with URL to the source code) as a script element to the DOM - head section.
- cskInjectJS: I created this function just to separate the actual configuration to add/load a list of custom javascripts. Right now it only has one custom javascript.
- Immediately invoked javascript code:
  1.  Load requireJS: The first thing I do is to load requireJS. You will notice that I am not referencing any object from the database (as a javascript object) and instead I am pointing directly to the require.js library on the web server where Oracle JET resides. Much easier to render directly from the web server!
  2. Load CSK_REQUIRE_CFG_JS: Next I load a custom javascript object (again added online so it can be updated in the future). My requirejs.config is very simple at this stage and I only included couple of library paths (JQuery and JQueryUI). We could configure additional paths in the future based on other requirements.
  3. You will notice that I am passing cskInjectJS as a callback function parameter to cskLoadJS function when I load the CSK_REQUIRE_CFG_JS object. This would ensure that cskInjectJS would get fired after the CSK_REQUIRE_CFG_JS javascript is loaded.
Object Name: CSK_REQUIRE_CFG_JS


Step 2: Add custom code to PT_HEADERPAGE.Activate (Page Activate PeopleCode)

This step is the same as what I did in 8.54. PT_HEADERPAGE is a header page that is part of all Fluid UI components and is mainly used for navigation purposes. We will be adding a line of code to inject our bootstrap javascript using peoplecode.


Custom PeopleCode:

/* CSK Custom Javascript Bootstrap for Fluid - Start */
AddJavaScript(HTML.CSK_FL_BOOTSTRAP_JS);
/* CSK Custom Javascript Bootstrap for Fluid - End */


Step 3: Add CSK_FL_BOOTSTRAP_JS to the custom Homepage Header (Classic)

Step 2 takes care of the Fluid UI and associated components. Although, in 8.55, the navigation header is unified and consistent across Classic and Fluid, the way Classic and Fluid get rendered are slightly different. The PT_HEADER page object is not used in Classic. This means that step 2 would have no effect in the Classic homepages and components. We could just add CSK_FL_BOOTSTRAP_JS to the Branding System Options (as I previously showed in my Branding 8.55 post). But I want to avoid that because I found that adding scripts to Branding System Options could invoke them more than once which is not desired in this case (I will write about this topic in a separate post later). Alternatively, I simply add CSK_FL_BOOTSTRAP_JS to my custom homepage header configured on my theme (refer: Branding 8.55 - Part 1).


Step 4: Inject Javascript

Now that we have our custom javascript object (CSK_FL_BOOTSTRAP_JS) injected into all Fluid UI and Classic homepages and components, we can use that as a configuration to further inject other javascript objects.

 
Right now, I only added one javascript object CSK_FL_DBNAME_JS (which I will describe in the next section) to cskInjectJS. But you can see how we can easily inject additional javascript objects as needed.

Creating an environment specific header for Non-Production databases:

In the previous section, I described how to create a javascript injection bootstrap for Fluid. I used Oracle JET to load JQuery and JQueryUI while managing dependencies using requireJS. Now, let us see an example of how we can inject a custom javascript using the bootstrap. The custom javascript is a rewrite of my previous javascript (created for 8.54 and extended for 8.55), to create an environment specific header for Non-Production databases.

Object Name: CSK_FL_DATABASE_JS


You can see how I used requireJS to take care of loading JQuery for me. All I am doing is mentioning the libraries that I need and let requireJS do the dependency management! A lot cleaner!

Note: Please remember to add the custom styles to both the Classic - Theme Style Sheet (CSK_BRAND_CLASSIC_TEMPL_FLUID) and the Global Override Style Sheet for Fluid (CSK_BRAND_FLUID_TEMPLATE). Refer Branding PT 8.55 - Part III for more details.

Results:

Classic:


Fluid:


Notes:

  1. Details of the environment used for this post: HCM 9.2 - PUM Image 17 - PeopleTools 8.55.03.
  2. If you find any inconsistent results while going through any of the steps detailed in this post then please make sure you bounce your web and app servers and purge the cache.

Wednesday, April 20, 2016

PeopleTools 8.55.x - Branding - Part III - Custom Macros and More

In my previous blog posts, we saw how we can brand PeopleSoft applications which are on PeopleTools 8.55 using the new Theme Macro Sets functionality (Part I and Part II). The Theme Macro Sets provides a great way to override targeted styles (e.g.: Header Logo, Icon images, background colors, etc.) using online configuration. The delivered Them Macro Set contains 177 macros which targets specific styles for some common Branding tasks.

Creating Custom Macros:

The concept and functionality of the Macro Set are great, but what if the 177 macros that are available do not meet our requirements? In Part II, I demonstrated how we can fall back to using the Theme - Fluid Global Override Style Sheet under such circumstances. In this section, I will detail how we can still bring those custom style sheet overrides into the Theme Macro Set as custom macros. Once we create the macros, we don't need to update the style sheet anymore. All we need to do is update the macros if there are any further changes (I guess making it a little user friendly depending on who is making the changes). This is particularly useful for customers who have a more dynamic branding which changes frequently depending on the time of the year vs being static after implementation.

Macros in Theme Macro Sets are nothing but variables used in the Theme - Fluid Global Override Style Sheet which are substituted at runtime.

Going back to my example in Part II, we used the following styles in the Theme - Fluid Global Override Style Sheet for changing the Dot Styling on the Fluid Landing Page Footer:

.lpfooter .dot.on {
  background: #EEEB4D;
}
.lpfooter .dot {
  background: #E8E29E;
  border: 2px solid #1d418c;
}

Let us re-write the above styles using custom variables (macros).

NavBar > Navigator > PeopleTools > Portal > Branding > Branding Objects

Edit the custom Fluid - Global Override Style Sheet (CSK_BRAND_FLUID_TEMPLATE) and update the styles as follows:

.lpfooter .dot.on {
  %CSK_FOOTER_DOT_ON_CSS;
}
.lpfooter .dot {
  %CSK_FOOTER_DOT_CSS;
}


Now, let us add these macros (variables) to our Theme Macro Set:

NavBar > Navigator > PeopleTools > Portal > Branding > Theme Macro Set

Select the custom Theme Macro Set and add the custom variables in the 'Macro List' grid:


Results:


Similarly, we can add other Fluid Style Sheet overrides as custom macro definitions if necessary.

Moving along, the rest of this blog details some advanced branding tasks which can be done in PT 8.55 similar to PT 8.54. I am posting links for those items here for continuity.

Creating an environment specific header for Non-Production databases:

Fluid Housekeeping Steps: Fluid Branding - 8.54 - Part 5B
Task steps: Fluid Branding - 8.54 - Part 5C

We will notice that the above steps would only work for the "Fluid" pages. To make it work on "Classic" pages, we need to perform some additional steps.

Step 1: Update the javascript to modify the jQuery selectors

// Display Database Name using jQuery once the document is ready;

var $jq1 = jQuery.noConflict();

$jq1(document).ready(function(){

   // Make sure we are only adding the div once;
   if ( $jq1("#cskdbnamecontainer").length === 0 ) {

      // Add div to display DB Name;
      $jq1( "#PT_HEADER, #ptbr_header_container").prepend( "<div id='cskdbnamecontainer' align='center'><span id='cskdbname'>Test Environment: %dbname</span><a href='#' id='cskdbnamehide'>Hide</a></div>" );

      // Add jQuery to hide the DB Name when the 'Hide' link is clicked;
      $jq1("#cskdbnamehide").click(function(){
         $jq1("#cskdbnamecontainer").hide();
      });

   }

});



You can see that I added an additional selector (#ptbr_header_container) to the jQuery so that the contained javascript code executes for Classic as well.

Step 2: Inject custom styles into Classic - Theme Style Sheet

NavBar > Navigator > PeopleTools > Portal > Branding > Branding Objects

Append the following styles to CSK_BRAND_CLASSIC_TEMPL_FLUID


Custom styles for reference:

/* Fluid - Display DBName for non-Prod environments */
#cskdbnamecontainer {
   height: 26px; 
   background-color: rgb(204,204,204);
}
#cskdbname {
   color: rgba(229,47,0,1);
   line-height: 26px;
   font-weight: bold;
   padding-right: 10px;
}


Step 3: Inject the custom javascript into Classic using Branding System Options

NavBar > Navigator > PeopleTools > Portal > Branding > Branding System Options


Results:



Adding Custom Links to Actions List Menu:

Fluid  Branding - 8.54 - Part 5C

Again, we will notice that the above steps would only work for the "Fluid" pages. In order to add custom links on "Classic" pages, we need to perform some additional steps to update the header definition (CSK_HEADER_FLUID).

NavBar > Navigator > PeopleTools > Portal > Branding > Define Headers and Footers





Note: The reason I am using a Static URL as the means to add the custom URL is because the URL object option does not seem to substitute the URL correctly. It appears to be a bug in 8.55.

Results:


Overriding the Favorite Icon:

Fluid Branding - 8.54 - Part 5C

Again, this will only work for "Fluid" pages.

Here are the steps to create a Favorite Icon for Classic Pages:

Step 1: Update custom javascript - CSK_FL_IR_JS

NavBar > Navigator > PeopleTools > Portal > Branding > Branding Objects

Update CSK_FL_IR_JS javascript object as follows:


Javascript for reference:

// Get Image URL for CSK_LOGO (FavIcon);
document.write(unescape("%3Cscript src='/psc/" + site + "/EMPLOYEE/EMPL/s/WEBLIB_FL_CSK.ISCRIPT1.FieldFormula.IScript_Set_Image_URL_Variable?var=cskFavIcon&img=CSK_LOGO_FAVICON' type='text/javascript'%3E%3C/script%3E"));

var $jq = jQuery.noConflict();
$jq(document).ready(function(){

  // If Classic;
  if ( $jq("#ptbr_header_container").length > 0) {

     // create div for favIcon
     var favIcon = document.createElement("LINK");

     // set attributes and innerHTML
     favIcon.setAttribute("rel","shortcut icon");
     favIcon.setAttribute("href", cskFavIcon);

     // insert favIcon div in the head element
     document.getElementsByTagName('head')[0].appendChild(favIcon);

  } else {

 
     // Replace Browser Favorite Icon(s);
     $jq('head link[href*=LOGO_FAVICON]').attr('href', cskFavIcon);
 
  }

});


Results:



Overriding the "Processing" Icon:

PT_PROCESSING_FMODE:


Fluid Branding - 8.54 - Part 5D