Using the Immediate Attribute

4-6 Web User Interface Developers Guide for Oracle Application Development Framework Figure 4–4 Immediate Attribute on an Input Component Setting immediate to true for an input component can be useful when one or more input components must be validated before other components. Then, if one of those components is found to have invalid data, validation is skipped for the other input components in the same page, thereby reducing the number of error messages shown for the page. Performance Tip: There are some cases where setting the immediate attribute to true can lead to better performance: ■ When you create a navigation train, and have a commandNavigationItem component in a navigationPane component, you should set the immediate attribute to true to avoid processing the data from the current page train stop while navigating to the next page. For more information, see Section 18.8.1, How to Create the Train Model. ■ If an input component value has to be validated before any other values, the immediate attribute should be set to true. Any errors will be detected earlier in the lifecycle and additional processing will be avoided. Using the JSF Lifecycle with ADF Faces 4-7 As another example, suppose you have a form with an input component used to search for a string with a command button configured to invoke the search execution, and another input text component used to input a date with an associated command button used to submit the date. In this example, we want to set the search input component and its button both to be immediate. This will allow the user to execute a search, even if an invalid string is entered into the date field, because the date input component’s converter is never fired. Also, because the search input text is set to immediate and the date input field is not, only the search input text will be processed. And because both fields are within the same form, if the user enters a valid date in the date field, but then performs a search and does not click the Save button, the entered value will still be displayed when the search results are displayed. Example 4–2 shows the code used for the two fields and two buttons. Example 4–2 Input Component and Command Components Using Immediate af:form af:inputText immediate=true label=Search value={mybean.search} valueChangeListener={mybean.searchValueChangeListener} af:commandButton immediate=true text=search actionListener={mybean.searchActionListener} [.... tags to render search result ....] af:inputText label=Date value={mybean.date} valueChangeListener={mybean.valueChangeListener} af:convertDateTime dateStyle=long af:inputText af:commandButton text=save actionListener={mybean.actionListener} af:form Figure 4–5 shows the lifecycle for this page when a user does the following: ■ Enters binky into the Date input field which is not a valid entry ■ Enters dress into the Search field ■ Clicks the Search button to execute the search on dress ■ Clicks the Save button to save the value binky as the date 4-8 Web User Interface Developers Guide for Oracle Application Development Framework Figure 4–5 Immediate Attribute on Both Command Component and Input Component When using the immediate attribute for editableValueHolder and actionSource components on the same page, note the following issues: ■ If an editableValueHolder component is marked as immediate, it will execute before the Update Model Values phase. This could be an issue when an immediate actionSource component requires data from an editableValueHolder component, as data entered into an editableValueHolder component is not available to the model until after the Update Model Values phase. If you have an immediate actionSource component, and that component needs data, then set immediate on the editableValueHolder fields as well. Then, you can call the getValue method on the editableValueHolder component and the local value will be returned. It will not have been pushed into the model yet, but it will be available on the component. ■ If an immediate editableValueHolder component fails validation, any immediate actionSource component will still execute. To use the immediate attribute: 1. On the JSF page, select the component that you want to be immediate. Using the JSF Lifecycle with ADF Faces 4-9

2. In the Property Inspector, expand the Behavior section and set the immediate

attribute to true.

4.3 Using the Optimized Lifecycle

ADF Faces provides an optimized lifecycle that you can use when you want the JSF page request lifecycle including conversion and validation to be run only for certain components on a page. For example, suppose you have an inputText component on a page whose required attribute is set to true. On the same page are radio buttons that when selected cause the page to either show or hide text in an outputText component, as shown in Figure 4–6 . Figure 4–6 Required Field and Boolean with Auto-Submit Also assume that you want the user to be able to select a radio button before entering the required text into the field. While you could set the radio button components to automatically trigger a submit action and also set their immediate attribute to true so that they are processed before the inputText component, you would also have to add a valueChangeEvent listener, and in it call the Render Response phase so that validation is not run on the input text component. Instead of having to write this code in a listener, ADF Faces allows you to set boundaries on the page that allow the lifecycle to run just on components within the boundary. In order to determine the boundary, the framework must be notified of the root component to process. This component can be determined in two ways: ■ Components: A region is an example of a component which the framework knows is a boundary. No matter what event is triggered inside a region, the lifecycle does not run on components outside the region. ■ Events: Certain events indicate a component as a root. For example, the disclosure event sent when expanding or collapsing a showDetail component see Section 8.8, Displaying and Hiding Contents Dynamically indicates that the showDetail component is a root, and so the lifecycle is run only on the showDetail component and any child components. The lifecycle may also be run on any components configured to listen for that disclosure event. Configuring a component to listen for events on root components in order to be processed is called cross-component refresh. Cross-component refresh allows you to set up dependencies so that the events from one component act as triggers for another component, known as the target. When any event occurs on the trigger component, the lifecycle is run on any target components, as well as on any child components of both the trigger and the target, causing only those components to be rerendered. This is considered a partial page rendering PPR. In the radio button example, you would set the radio buttons to be triggers and the panelGroupLayout component that contains the output text to be the target, as shown in Example 4–3 . Example 4–3 Example of Cross-Component Rendering af:form af:inputText label=Required Field required=true 4-10 Web User Interface Developers Guide for Oracle Application Development Framework af:selectBooleanRadio id=show autoSubmit=true text=Show value={validate.show} af:selectBooleanRadio id=hide autoSubmit=true text=Hide value={validate.hide} af:panelGroupLayout partialTriggers=show hide id=panel af:outputText value=You can see me rendered={validate.show} af:panelGroupLayout af:form Because the autoSubmit attribute is set to true on the radio buttons, when they are selected, a SelectionEvent is fired, for which the radio button is considered the root. Because the panelGroupLayout component is set to be a target to both radio components, when that event is fired, only the selectOneRadio the root, the panelGroupLayout component the root’s target, and its child component the outputText component are processed through the lifecycle. Because the outputText component is configured to render only when the Show radio button is selected, the user is able to select that radio button and see the output text, without having to enter text into the required input field above the radio buttons. For more information about how the ADF Faces framework uses PPR, and how you can use PPR throughout your application, see Chapter 7, Rerendering Partial Page Content.

4.3.1 What You May Need to Know About Using the Immediate Attribute and the Optimized Lifecycle

There may be cases where PPR will not be able to keep certain components from being validated. For example, suppose instead of using an outputText component, you want to use an inputText component whose required attribute is set to true, inside the panelGroupLayout component, as shown in Example 4–4 . Example 4–4 inputText Component Within a panelGroup Component Will Be Validated with Cross-Component PPR af:form af:selectBooleanRadio id=show2 autoSubmit=true text=Show value={validate.show2} af:selectBooleanRadio id=hide2 autoSubmit=true text=Hide value={validate.hide2} af:panelGroupLayout partialTriggers=show2 hide2 af:inputText label=Required Field required=true rendered={validate.show2} af:panelGroupLayout af:form In this example, the inputText component will be validated because the lifecycle runs on the root the selectOneRadio component, the target the panelGroupLayout component, and the target’s child the inputText component. Validation will fail because the inputText component is marked as required and there is no value, so an error will be thrown. Because of the error, the lifecycle will skip to the Render Response phase and the model will not be updated. Therefore, the panelGroupLayout component will not be able to show or hide because the value of the radio button will not be updated. For cases like these, you can skip validation using the immediate attribute on the radio buttons. Doing so causes the valueChangeEvent on the buttons to run before the Process Validation phase of the inputText component. Then you need to add a valueChangeListener handler method that would call the Render Response phase Using the JSF Lifecycle with ADF Faces 4-11 thereby skipping validation of the input component, and set the values on the radio buttons and input component. Example 4–5 shows the JSF code to do this. Example 4–5 Using the immediate Attribute and a valueChangeListener af:form af:selectOneRadio immediate=true valueChangeListener={validate.toggle} id=show2 autoSubmit=true text=Show value={validate.show2} af:selectOneRadio id=hide2 autoSubmit=true text=Hide value={validate.hide2} af:panelGroupLayout partialTriggers=show2 hide2 af:inputText label=Required Field required=true rendered={validate.show2} af:panelGroupLayout af:form Example 4–6 shows the valueChangeListener code. Example 4–6 valueChangeListener Sets the Value and Calls Render Response public void toggleValueChangeEvent vce { setShow2Boolean.TRUE.equalsvce.getNewValue; FacesContext.getCurrentInstance.renderResponse; }

4.3.2 What You May Need to Know About Using an LOV Component and the Optimized Lifecycle