Showing posts with label ADF Faces. Show all posts
Showing posts with label ADF Faces. Show all posts

AdfRichInputText.getSubmittedValue() instead of AdfRichInputText.getValue().

I was dealing with an interesting bug today and would like to share my experience with you ,

I have a search input text box and a submit button in UI ( all are ADF faces components). Submit button click event calls a javascript method and  process  search query with input text box value.

It works as expected in all browsers except IE 11. So I started debugging on javascript with IE developer tool and noticed that AdfRichInputText.getValue() is null ,but same javascript works for lover version of IE , Firefox, chrome and safari. Then I played with AdfRichInputText.getSubmittedValue() and it returns search query .

Here is the catch. AdfRichInputText.getValue() returns local value and AdfRichInputText.getSubmittedValue() returns submitted value of editable component.Though my request was new and local value holds null and submitted value holds actual value.

But still I don't understand how it worked in other browsers

Reference: 
http://docs.oracle.com/cd/E23943_01/apirefs.1111/e12046/org/apache/myjs/trinidad/component/AdfUIEditableValue.html 

Environment : Webcenter spaces 11.1.1.7 with IE 11 patch
Browser: IE 11


Disable auto-complete feature for editable component.


 
<af:resource type="javascript">
   
      function disableAutoComplete(evt) {
      var comp = evt.getSource();
      comp.setAutoComplete('off');
      evt.close();
      }

    </af:resource>


 <af:inputText label="" id="pt_it1">
<af:clientListener method="disableAutoComplete" type="focus"/>
</af:inputText>

If you are interested to suppress auto-complete feature for browser form, you can refer Frank Nimphius's blog link



Handy code for getting ADF faces component from View root.




    private UIComponent findComponentOnPage(String compId) {

        UIViewRoot root = FacesContext.getCurrentInstance().getViewRoot();
        root.invokeOnComponent(FacesContext.getCurrentInstance(), compId,
                               new ContextCallback() {
                public void invokeContextCallback(FacesContext facesContext,
                                                  UIComponent uiComponent) {
                    comp = uiComponent;
                }
            });
        return this.comp;
    }

Reference : http://www.oracle.com/technetwork/developer-tools/adf/downloads/58-optimizedadffacescomponentsearch-175858.pdf

Programmatically changing validation property in view criteria


In many cases we need to conditionally change the validation property of view criteria  ( we can change required / Selectively Required / Optional property in Query panel ).There is a method called setRequiredString(String) in ViewCriteriaItem object for achieving this requirement. Argument of this method is “Optional ” or “Required” or “SelectivelyRequired”. I am calling changeValidation() from queryOperationListener of af:Query component.In UI you can refresh your query component by self reference of partial trigger. Below code is self explanatory .  :) :) :)


<af:query id="qryId1" headerText="Search" disclosed="true"
                    value="#{bindings.Search_region_Name.queryDescriptor}"
                    model="#{bindings.Search_region_Name.queryModel}"
                    queryListener="#{backingBeanScope.BeanName.processQuery}"
                    queryOperationListener="#{backingBeanScope.BeanName.queryOperationListener}"
                    partialTriggers="::qryId1"/>

Managed Bean Code
public void queryOperationListener(QueryOperationEvent queryOperationEvent) { JSFUtils.resloveMethodExpression("#{bindings.Employees1.collectionModel.makeCurrent}", Object.class, new Class[] { QueryOperationEvent.class }, new Object[] { queryOperationEvent }); if (queryOperationEvent.getOperation().equals(QueryOperationEvent.Operation.CRITERION_UPDATE)) { changeValidation(); } }

    private void changeValidation() {         DCDataControl dataControl =             BindingContext.getCurrent().findDataControl("xxxAppModuleDataControl");         ApplicationModule am =             (ApplicationModule)dataControl.getDataProvider();         ViewObject vo = am.findViewObject("VO_Instance_Name");         ViewCriteria viewCriteria =             vo.getViewCriteriaManager().getViewCriteria("View_Criteria_Name");         ArrayList criteriaItems =             (ArrayList)((ViewCriteriaRow)viewCriteria.getRows().get(0)).getCriteriaItems();         Iterator iterator = criteriaItems.iterator();         while (iterator.hasNext()) {             ViewCriteriaItem item = (ViewCriteriaItem)iterator.next();             if (item.getName().equalsIgnoreCase("View_Attribute_Name")) {                 ((ViewCriteriaItem)criteriaItems.get(2)).setRequiredString("SELECTIVELY_REQUIRED");                 if ((null != item.getValue())) {                     ((ViewCriteriaItem)criteriaItems.get(0)).setRequiredString("Optional");                     ((ViewCriteriaItem)criteriaItems.get(1)).setRequiredString("Optional");                 } else {                     ((ViewCriteriaItem)criteriaItems.get(0)).setRequiredString("SelectivelyRequired");                     ((ViewCriteriaItem)criteriaItems.get(1)).setRequiredString("Required");                 }             }         }     }

Attribute value from Choice List



In many instances we have come up across a common issue where we need to get the actual attribute from a drop down but we used to get the index value. As a workaround we wrote backing bean methods to get the attribute value from View Object.
So now just keep that workaround aside and try with this new approach.
An expression like #{bindings.JobId.inputValue} would return the internal list index number when JobId was a list binding(LOV of choice list type). To get the actual JobId attribute value, you needed to use #{bindings.JobId.attributeValue} .The #{bindings.JobId.attributeValue} expression will return the attribute value corresponding with the selected index in the choice list.

Refresh Query component



/**
* Method for refreshing af:query component
* @param queryComponent
*/
public static void refreshQueryComponent(RichQuery queryComponent) {
QueryModel queryModel = queryComponent.getModel();
QueryDescriptor queryDescriptor = queryComponent.getValue();
queryModel.reset(queryDescriptor);
queryComponent.refresh(FacesContext.getCurrentInstance());
}

Highlighting row in a single selection table



/**
* Method for highlighting row in a single selection table
* @param Key
*/
public static void SelectTableRow(Key key, RichTable table) {
if (table == null) {
return;
}
if (key == null) {
key = new Key(new Object[] { 0 });
}
RowKeySet rks = table.getSelectedRowKeys();
if (rks == null) {
rks = new RowKeySetImpl();
} else {
rks.removeAll();
}
List keyList = new ArrayList();
keyList.add(key);
rks.add(keyList);
table.setSelectedRowKeys(rks);
}

Method for getting selected row from ADF Table



/**
* Method for getting selected row from Table
* @param uiTable
* @param iteratorName
* @return Row
*/
public static Row selectedRowFromTable(RichTable uiTable,
String iteratorName) {
Row row = null;
RowKeySet rowKeySet = uiTable.getSelectedRowKeys();
if (rowKeySet != null) {
Iterator rowIterator = rowKeySet.iterator();
Key key = (Key)((List)rowIterator.next()).get(0);
DCIteratorBinding voIterator =
IteratorUtils.getDCIteratorBinding(iteratorName);
RowSetIterator rowSetIterato = voIterator.getRowSetIterator();
row = rowSetIterato.getRow(key);
}
return row;
}

Declarative way to populate child table’s data into Parent table’s column.



There are many ways to populate child table’s data into parent table’s column value. I have developed and posting a sample application for populating child table’s data in to parent table’s column value ( Foreign-key relation is one to many) with view assessors trick :P 

Download Application : Link 

Environment
Jdeveloper version: 11.1.1.5.0
Database: Oracle XE
Schema: HR

UI Screen looks like


Here I am populating all the employees under a department in to Department grid's row.  



  1. Create an ADF Web Application and model and view projects.
  2. Create business components like below structure.

3. Create an Application module like below structure.























4. Create Department view and add a transient attribute(Empname) 

DepartmentsView 











5. Create Employees view 











6.Create a view criteria( EmployeesViewCriteria ) in Employees view. See below picture. 





7.Create List of Values for EmpName attribute in Departments view. See below pics.






























8. Go to view accessors option in Departments view and click the pencil( Edit ) button.










9. Shuttle EmployeeViewCriteria and give value for viewcritera bind variable.Here DepartmentId is the attribute name from Departments view. 






















10. Create a JSF page (Main.jspx) and drop DepartmentsView collection from data controll as a table. 

11. Remove default component from EmpName column and add a new iterator component like below pic.