ADF Faces: Suppress Validation on PPR request
By frank.nimphius | May 7, 2008
Another lost sample from orablogs for self study. The workspace contains code that suppresses ADF validation if the request is from partial page rendering. Note that this uses an internal API. A public API is available in Jdeveloper 11 in where we use Trinidad.
Frank
Topics: ADF Faces | No Comments »
ADF Faces RC: How-to configure a custom Splash Screen
By frank.nimphius | May 7, 2008
Splash screens, or enduser entertainment as I like to put it, show at the beginning of initial page loading until all resources become available for the user to start his work. ADF Faces RC components provide a splash screen that by default shows a rotating “O” for Oracle with an associated message letting the user know that application initialization is in progress. For your production applications, you may want to change the splash screen to show a custom image that fits to your corporate identity and logo. This how-to explains how to do this.
Frank
Topics: ADF Faces RC | No Comments »
ADF Faces: ADF Faces Tree Drilldown Example
By frank.nimphius | May 2, 2008
Another lost example: The workspace linked by this blog entry shows how to use a command link to drill down to detail records shown in a table.
The drilldown functionality - though not shown as a stand alone example - is documented by Steve Muench in the context of the ADF BC version in the SRDemo and the ADF Business Components developer guide. In this blog entry I'll give you two examples - the one provided in the developer guide and one less declarative but code centric example.
The ADF BC Developer Guide version
The ADF BC Developer Guide version sets the row currency for the data displayed in the form by clicking on the tree node links. To get to a specific user entry, you click the location node, expand the department node and then click onto the user name entry.
Clicking the department node entry shows the first record by default, which allows you to build an input form with navigation buttons. While this works nicely, having to click on each and every tree node along the path down to the user entry may not be considered user friendly.
Firstly, make sure you created iterators for each of the ViewObjects invloved: LocationsView, DepartmentsView, EmployeesView
This solution is implemented through the setCurrentRowWithKey operation, which is exposed as an operation on the LocationView, DepartmentsView and EmployeesView. Open the pageDef file in the Structure Window and select the bindings node.
From the context menu select the option to create a new Action. Select the LocationView instance that represents the top view in the tree structure. Choose the setCurrentRowWithKey option from the drop down.
Its important to set the rowKey value to #{node.rowKeyStr} so that the selected node's key value is passed to the operation. the "node" string is a variable name contained in the page when building the tree and you have to type it into the value field (the ExpressionLanguage builder doesn't see this variable name)
After building the action, make sure you give it a good and readable name by changing the default name in the property inspector for the action.
Next step is to create a binding of the tree component to a managed bean. The binding is used later to detect the depth of the tree, which is important for the command link to access the right setCurrentRowsWithKey action.
The tree nodes are defined by three command link components, according to the expected tree depth of location -- department -- employees.
Each of the command links is displayed or hidden based on one of the following conditions added to the "rendered" property
#{TreeManagedBean.treeHandler.depth==0}
#{TreeManagedBean.treeHandler.depth==1}
#{TreeManagedBean.treeHandler.depth==2}
This means that e.g. the command link with the ActionListener set to execute the setCurrentRowWithKey operation for the employees view, is shown or hidden by #{TreeManagedBean.treeHandler.depth==2}
Last, but not least, each of the command links needs to be linked to one of the setCurrentRowWithKey actions.
This way, when the node is clicked on, the underlying ViewObject row currency is set to the selected row. Also note that the command links don't use PPR (partial submit = false).
-
<h:panelGroup>
-
<af:commandLink text="#{node}" partialSubmit="false"
-
id="nodeAction1"
-
actionListener="#{bindings.setCurrentLocationRowWithKey.execute}"
-
rendered="#{TreeManagedBean.treeHandler.depth==0}"/>
-
<af:commandLink text="#{node}" partialSubmit="false"
-
id="nodeAction2"
-
rendered="#{TreeManagedBean.treeHandler.depth==1}"
-
actionListener="#{bindings.setCurrentDepartmentsRowWithKey.execute}"/>
-
<af:commandLink text="#{node}" partialSubmit="false"
-
id="nodeAction3"
-
rendered="#{TreeManagedBean.treeHandler.depth==2}"
-
actionListener="#{bindings.setCurrentEmployeesRowWithKey.execute}"/>
-
</h:panelGroup>
-
-
Note that for the JSF form to show the selected employee, the input form must be based on the EmployeeView instance contained in the LocationView tree.
Custom example
The custom example solves the usability concern of the version documented in the ADF BC developer guide so tha only the leaf nodes are shown as hyperlinks. Later, in the implementation, you will see that the risk with this version lies in how the node tree key is parsed.
As for the documented ADF BC tree drill down example, you need to create iterator bindings for all the ViewObject instances that are involved. Also you need to create a binding from the tree component to a managed bean.
Instead of using three command links that are used in the previouse example, you use one output text component and one command link. The command link is set to partial submit and also has an id assigned to it so it triggers the refresh of the JSF input form.
Note that the output text component is rendered for all tree depth that are below 2, whcih means for locations and employees.
The ActionListener property on the commandLink component is set to #{TreeManagedBean.nodeSelected}, which is a managed bean method.
-
public void nodeSelected(ActionEvent actionEvent) {
-
-
String rowKeyStr = getTreeHandler().getRowKey().toString();
-
String[] path = rowKeyStr.split(", ");
-
-
if (getTreeHandler().getDepth()==2) {
-
int locIndx = new Integer(path[0].substring(1)).intValue();
-
int depIndx = new Integer(path[1].substring(0)).intValue();
-
int empIndx = new Integer(path[2].substring(0,path[2].indexOf("]"))).intValue();
-
-
// System.out.println(locIndx);
-
// System.out.println(depIndx);
-
// System.out.println(empIndx);
-
-
FacesContext fctx = FacesContext.getCurrentInstance();
-
ValueBinding vb = fctx.getApplication().createValueBinding("#{bindings.LocationsView1Iterator}");
-
DCIteratorBinding dciterLocationsView = (DCIteratorBinding)vb.getValue(fctx);
-
dciterLocationsView.getRowSetIterator().setCurrentRow(dciterLocationsView.getRowAtRangeIndex(locIndx));
-
-
vb = fctx.getApplication().createValueBinding("#{bindings.DepartmentsView3Iterator}");
-
DCIteratorBinding dciterDepartmentsView = (DCIteratorBinding)vb.getValue(fctx);
-
dciterDepartmentsView.getRowSetIterator().setCurrentRow(dciterDepartmentsView.getRowAtRangeIndex(depIndx));
-
-
vb = fctx.getApplication().createValueBinding("#{bindings.EmployeesView4Iterator}");
-
DCIteratorBinding dciterEmployeesView = (DCIteratorBinding)vb.getValue(fctx);
-
-
int empRangeSize = dciterEmployeesView.getRangeSize();
-
int empRangeIndx = 0;
-
int empRowIndx = 0;
-
-
if (empIndx + 1> empRangeSize){
-
empRangeIndx = empIndx/ empRangeSize;
-
empRowIndx = empIndx % empRangeSize;
-
dciterEmployeesView.getRowSetIterator().setRangeStart(dciterEmployeesView.getRangeSize()*empRangeIndx);
-
empIndx = empRowIndx;
-
}
-
-
dciterEmployeesView.getRowSetIterator().setCurrentRow(dciterEmployeesView.getRowAtRangeIndex(empIndx));
-
//additional partial target needed to be set
-
AdfFacesContext.getCurrentInstance().addPartialTarget(formHandler);
-
}
-
}
Because the user clicks on an employee enttry only, the manage bean method parses the row key, which comes in the format of [location index, department index, employee index]
For example --- [0, 1, 13] identifies the 14th employee node of the second departments node under the first location
Knowing about the tree structure, this information is then used to determine the current row and setting it (similar to what clicking each of the commanLink does in the first example)
-
FacesContext fctx = FacesContext.getCurrentInstance();
-
ValueBinding vb = fctx.getApplication().createValueBinding("#{bindings.LocationsView1Iterator}");
-
DCIteratorBinding dciterLocationsView = (DCIteratorBinding)vb.getValue(fctx);
-
dciterLocationsView.getRowSetIterator().setCurrentRow(dciterLocationsView.getRowAtRangeIndex(locIndx));
The code line above sets the currentRow for the locations iterator based on the location tree node that the selected employee is a member of.
If you access ViewObjects that use page ranges, which is recommended to not always query the whole data, you must be aware of the possibility that a selected node - eg. employee node in this example - is not in the first (default) range. The range by default is set to 10 records. This setting is defined on the iterator binding properties.
To access the correct row, you need to get the range size out of the employee index. E.g. employee 23 means that it is the 4th record (counting starts by 0) in the 2nd range (also counting from zero)
-
int empRangeSize = dciterEmployeesView.getRangeSize();
-
int empRangeIndx = 0;
-
int empRowIndx = 0;
-
-
if (empIndx + 1> empRangeSize){
-
empRangeIndx = empIndx/ empRangeSize;
-
empRowIndx = empIndx % empRangeSize;
-
dciterEmployeesView.getRowSetIterator().setRangeStart(dciterEmployeesView.getRangeSize()*empRangeIndx);
-
empIndx = empRowIndx;
-
}
Setting the range start ensures that the employee index (3 if the index number was 23) can be looked up
To run the application, you need to
Get the workspace from here
- Copy adf-faces-impl.jar from jdeveloper_10131_3984\jlib to AdfFacesTreeSample\ViewController\public_html\WEB-INF\lib and AdfFacesTreeSample\ViewController2\public_html\WEB-INF\lib
- Copy jsf-impl.jar from jdeveloper_10131_3984\jsf-ri to AdfFacesTreeSample\ViewController\public_html\WEB-INF\lib and AdfFacesTreeSample\ViewController2\public_html\WEB-INF\lib
- Create a named database connection hrconn in Jdeveloper
- Run TreeNode.jsp or TreeNode2.jsp
Topics: ADF Faces | No Comments »
JDeveloper 11 TP4 is out on OTN
By frank.nimphius | May 2, 2008
Just in case you haven't seen it yet, JDeveloper 11 Technology Preview 4 is out (Get it here on OTN). Please play with it and report problems, enahncement requests and questions on the JDeveloper 11 forum.
If you experience an issue on one of the previous releases, make sure they reproduce on TP4 before reporting them. Future oriented as we are we wont handle TP3 issues that don't reproduce in TP4.
Frank
Topics: General News | No Comments »
ADF Faces RC: Expanding an af:tree node by clicking onto its label
By frank.nimphius | April 24, 2008
Tree nodes in ADF Faces RC are expanded at runtime by clicking onto the plus icon next to the folder name. For improved usability you may want to allow users to click onto the folder name as well to expand the a node; same for closing a folder node.
This functionality, which is not provided by default, can be added using the ADF Faces RC client framework using a little bit of JavaScript. Read More
Frank
Topics: ADF Faces | No Comments »
Your call ! How to handle the application lifeycycle with JDeveloper?
By frank.nimphius | April 23, 2008
On her blog, Susan Duncan from the JDeveloper team asks for input regarding ALM software that you use or like JDeveloper to work with.
"Some of the areas that I've always been interested in - as a consultant, a teacher, a curriculum developer or as a Product Manager - are standards, methodology and development process: From Designer to JDEV, from CDM to Agile, from ClearCase to SVN, from IE to UML and so much more. Now we call that ALM - Application Lifecycle Management - the management of the lifecycle development practices (requirements, build, test, change control, defect mgmt etc) fused together through application of process, reporting, traceability and collaboration.
Here in JDeveloper land we are always looking at ways to improve both our tooling and the developer experience so I've put together a survey to find out what ALM tools you are using today. We're looking into adding better integration with ALM tools and the results of the survey will ensure that we move in the right direction."
If you have an opinion, please fill in the survey and win a "thank you with a smile" :
Frank
Topics: Uncategorized | No Comments »
ADF Faces: Configuration with ADF BC on Tomcat 6 with MySQL 5
By frank.nimphius | April 22, 2008
A posting on OTN explains how to setup and run ADF Faces with Tomcat and MySQL. I didn't test this configuration, but think that this information is worth to share: OTN Post
Frank
Topics: ADF Faces | No Comments »
Blogbuster’s Orablog Content partly “Recovered”
By frank.nimphius | April 18, 2008
Thanks to Gerard Davison who pointed me to http://web.archive.org, I could partially recover the lost content. However, most of the entries no longer contain the images I uploaded. This makes reading the "old" postings a bit harder, but at least you get the information and - most important - the workspaces where examples where provided. I updated the following page with the content
Frank
Ps.: Now I understand what "second life" really means
Topics: General News | No Comments »
orablogs.com domain is gone - definitively! But there are good news as well!
By frank.nimphius | April 18, 2008
Just today I recognized that orablogs.com is up again. Unfortunately this domain is used by another site that has nothing to do with what it was originally used for. I suggest to remove all your bookmarks to orablogs to prevent you accidentally getting onto this site.
My orablogs content is gone and recovering the content on my new blog http://thepeninsulasedge.com/frank_nimphius/ would take more time than I have to spend. My strategy thus is to recover those samples that I see a demand for or that are explicitly requested on the JDeveloper forum on OTN. This recovery will include the workspaces only, with a few hints on how to set them up. I'll continue to create new JDeveloper 10.1.3 content for interesting usecases.
Life goes on and JDeveloper 11 is coming closer. To make sure developers find enough code examples for the Fusion development stack in JDeveloper 11, I'll focus more on this new release. To make it easier for readers to find these code examples, and to make sure history doesn't repeat itself, I found a new home for this content on OTN: Oracle ADF Code Corner". All the documents on this site will be linked from my blog at http://thepeninsulasedge.com/frank_nimphius/ as well; plus they will be aggregated in the JDeveloper blog aggregator.
Another exciting project that Lynn Munsinger and I are working on is book writing. We are close to signing a contract to write a book book about Fusion development that will include lots of code examples about ADF and ADF Faces RC. I think the last push I needed to really make me looking forward to this project is the problem of the lost content on orablogs. I don't have more to say about the book writing right now, but Lynn and I plan to keep you updated on our blogs after we signed the contract. This way you now what to expect and the state it is in. The publishing date will be sometime in the middle of next year. However the book writing plan should not impact my blogging habits or my visibility on the OTN forums, I will just work harder to produce more content.
Frank
Topics: General News | No Comments »
ADF Faces RC: intercept the table query filter condition added by the application user
By frank.nimphius | April 15, 2008
A new feature of ADF Faces RC is the ability for users to filter the result set of a table at runtime. For this, the developer selects the filter option on the ADF binding dialog that is shown for the table when dragging a ViewObject onto an ADF Faces RC page. At runtime, application users use an input field in the table header to provide query conditions that are appended to the underlying query defined in teh VO by the developer. A question on the OTN forum was how to intercept the query condition added by the users.
Read the how-to and get the JDeveloper workspace
Also worth bookmarking: Oracle ADF Code Corner
Frank
Topics: ADF Faces | No Comments »
« Previous Entries
