Wednesday, March 9, 2011

Dynamic resizing for popup dialogs

In some specific circumstances you may need to fulfill a requirement that would have a popup dialog (containing for example, an adf table), resize itself dynamically based on the browser viewing size. This behavior is similar to how the panelCollection component handles the popup window that is invoked from the "detach" menu item. By default, the panelWindow, which is the immediate child of the popup, height (ContentHeight) and width (ContentWidth)property values are not set. This enables the popup to launch with the default size settings for the panelWindow:




















Of course you can always set the values on these 2 properties to alter the size on the panelWindow itself. Unfortunately, the trick will be to calculate the browser view dimensions in java, which in turn can be then passed/set on each of the content (width and height) property values. Now this issue can be solved by getting the browser view dimensions through javascript (there are plenty examples on the web for doing so), but then the next challenge would be to figure out a clever way on how to pass these (javascript based) values to the panelWindow component properties.

Fortunately, there is a much better way to get these dimensions through the ADF JavaScript API. In addition, I can also use javascript to pass the retreived dimension values to the panelWindow itself. The following javascript code fragment will do the trick:

function openPopup(popupId, panelWindowId)
{
return function(event)
{
var agent = AdfAgent.AGENT;
var windowWidth = agent.getWindowWidth();
var windowHeight = agent.getWindowHeight();
var popup = AdfPage.PAGE.findComponentByAbsoluteId(popupId);
var panelWindow = popup.findComponent(panelWindowId);
panelWindow.setContentWidth(Math.max(100, windowWidth-60));
panelWindow.setContentHeight(Math.max(100, windowHeight-80));


if(popup != null)
popup.show();
else
popup.hide();
}
}

Also note that this function also takes care of displaying the popup. Normally, you would invoke the popup through the af:showPopupBehavior (operations based tag). This tag is simply replaced by the af:clientListener tag. For example:

af:clientListener type="action" method="openPopup('popupId','panelWindowId')"

Using this methodology the working results are as such:



















So there you have it, a nice resizable popup without having to write alot of code. Thanks to my good friend and colleague Frank Nimphius on setting me on the right path in discovering this solution.

I have provided the code sample zip here