wesleyhales.com

JSF AjaxSlider Component

07 January 2007

Java |

This is the first release of my AjaxSlider component. This version works with JSP and Facelets and also extends FacesEvent to provide it's own event/listener. Many thanks to Jonas Jacobi and John Fallows for putting together a great book (Pro JSF and Ajax).

I'm also using the slider functions from the Script.aculo.us library


This component in hardly complete and bug free, so any help in debugging is appreciated

Download the component source, examples, and all necessary resources here(I also included my Idea project file in the download). I will be adding this code to JSF-Comp repository hopefully within the next day or two.

Usage Option 1

You can use AjaxSlider with the following options. This will only use listeners or submit the SliderEvent to a backing bean. It will give you more control in case you do not want to store the list, used in your datatable, in the session (described in option 2). Both listeners are not required, I just added them here to show examples on usage.

 
 
 xmlns:hc="http://www.halesconsulting.com/jsf" 
 xmlns:ac="http://ac"> 
 
 <style> 
 .range{ 
 width: 200px; 
 background: transparent url("/facelet-sandbox/images/demo_bg.gif") no-repeat center; 
 height: 20px; 
 } 
 
 .Mytest{ 
 background-color:transparent; 
 } 
 
 .trailer{ 
 background: transparent url("/facelet-sandbox/images/demo_bg_over.gif") no-repeat 0 7px; 
 height: 20px; 
 width: 114px; 
 } 
 
 .track{ 
 width: 200px; 
 height: 20px; 
 position: absolute; 
 } 
 
 .handle{ 
 position: absolute; 
 width: 10px; 
 height: 25px; 
 background:url("/facelet-sandbox/images/demo_arrow.gif") no-repeat center; 
 cursor: col-resize; 
 left: 114px; 
 } 
 
 </style> 
 
 <a4j:form id="form1" > 
 
 <hc:ajaxSlider sliderListener="#{sliderBean.doShow}" 
 onSlide="true" 
 onChange="true" 
 storeResults="false" 
 trackStyleClass="track" 
 styleClass="Mytest" 
 startRange="0" 
 endRange="50000" 
 increment="10000" 
 rangeStyleClass="range" 
 trailer="true" 
 trailerStyleClass="trailer" 
 handleStyleClass="handle" 
 handleValue="1" 
 id="slider_1" ><hc:sliderListener type="com.halesconsulting.web.action.MySliderListener" /></hc:ajaxSlider> 
 
 </a4j:form> 
 
 

Usage Option 2

Here we store the list from the UIData object in the session by setting storeResults="true". Obviously, using this option will depend on your situation. But to get the best user experience out of the slider interaction, this was the only way.

 
 xmlns:hc="http://www.halesconsulting.com/jsf" 
 xmlns:ac="http://ac"> 
 
 <style> 
 .range{ 
 width: 200px; 
 background: transparent url("/facelet-sandbox/images/demo_bg.gif") no-repeat center; 
 height: 20px; 
 } 
 
 .Mytest{ 
 background-color:transparent; 
 } 
 
 .trailer{ 
 background: transparent url("/facelet-sandbox/images/demo_bg_over.gif") no-repeat 0 7px; 
 height: 20px; 
 width: 114px; 
 } 
 
 .track{ 
 width: 200px; 
 height: 20px; 
 position: absolute; 
 } 
 
 .handle{ 
 position: absolute; 
 width: 10px; 
 height: 25px; 
 background:url("/facelet-sandbox/images/demo_arrow.gif") no-repeat center; 
 cursor: col-resize; 
 left: 114px; 
 } 
 
 </style> 
 
 
 <a4j:form id="form1" reRender="list-body" ajaxSubmit="true"> 
 
 <a4j:region id="stat1"> 
 
 <a4j:outputPanel id="slider-body"> 
 
 <hc:ajaxSlider sliderListener="#{sliderBean.doShow}" 
 for="carList" 
 forValRef="inventoryList.carInventory" 
 filterBy="getMileage" 
 onSlide="true" 
 onChange="true" 
 storeResults="true" 
 trackStyleClass="track" 
 styleClass="Mytest" 
 startRange="0" 
 endRange="50000" 
 increment="10000" 
 rangeStyleClass="range" 
 trailer="true" 
 trailerStyleClass="trailer" 
 handleStyleClass="handle" 
 handleValue="1" 
 id="slider_1" ><hc:sliderListener type="com.halesconsulting.web.action.MySliderListener" /></hc:ajaxSlider> 
 
 </a4j:outputPanel> 
 
 <a4j:outputPanel id="list-body"> 
 
 <t:dataTable id="carIndex" 
 
 </t:dataTable> 
 
 <t:dataTable id="carList" value=#{inventoryList.carInventory} 
 
 <ac:ajaxDataScroller id="scroll_1" 
 
 </a4j:outputPanel> 
 
 <a4j:status for="stat1" forceId="true" id="ajaxStatus"> 
 <f:facet name="start"> 
 <div id="loading-modal"></div> 
 </f:facet> 
 </a4j:status> 
 
 </a4j:region> 
 
 </a4j:form> 
 

All of the attribute descriptions are available in the faces-config.xml file if you have any questions. Feedback is more than welcomed and appreciated.

JSF Ajax Filter/Slider with UIData

31 December 2006

Java |

In any RIA where h:dataTable is used, probably 90% of the time, you will need a filter in the same view/page as the dataTable. A Filter can be anything from a list of links, a select many list, or in this example, a slider.

At first, I thought about just creating the component and have it add the value of the slider to a request parameter so that the backing bean could have access to the value. The backing bean could then loop through the list and compare the slider value to the object, then present the filtered data. This is probably the most common and easiest option in most cases, but it seems there are too many drawbacks in developing this way.

  1. This custom config leads to repeated code scattered throughout each backing bean that makes use of the filter.
  2. Even if you abstract this functionality, it would be just as easy, and beneficial, to create a custom component to handle this. You could create a component that could filter any other component that makes use of UIData.
  3. If you have 5 filters in 1 view, and they all create a combined criteria for your dataTable list, it would be nice if this logic was hidden under the hood of the component and everything played well together.

A UIData filtering component should be much like the dataScroller component. It should have a "for" attribute with the id of your component to be filtered. We can provide attributes like range, start position, and all other common component attributes. It would also be nice to have a "depends" attribute that would allow a comma delimeted list of other filter component id's that would provide a state or limits for this components functionality.

Although my slider component is 95% complete, I guess I'm using this post as a semi-blueprint/laying some thoughts on paper. Filtering is an important part of displaying tabular, or any, data and I haven't seen any open source components addressing it. If anyone reading knows of JSF filtering, please leave a url. I plan on submitting the slider to JSF-Comp or any other project willing to take it within the next week.

Ajax4Jsf Modal Loading Windows

26 December 2006

Java |

Ajax4Jsf's status tag (a4j:status) has alot of potential, but currently it's functionality is limited. With the combination of Lightbox 2.0, or basically any javascript developed to build the dom, you can achieve the look of any modal "Loading..." window.

Since the status tag does not include capability to fire javascript events(as of yet), we will use the modified lightbox script to go ahead and write everything to the dom, then let the a4j:status tag to hide it until we make an Ajax call.

*Update - I recently created a working demo application for this modal. Read the updated blog entry here.

Facelet Source

This just shows basic usage with the A4J framework

 
 

 <script type="text/javascript" src="/facelet-sandbox/js/scriptaculous-js-1.6.5/lib/prototype.js"></script> 

 <script type="text/javascript" src="/facelet-sandbox/js/scriptaculous-js-1.6.5/src/scriptaculous.js?load=effects"></script> 
 <script type="text/javascript" src="/facelet-sandbox/js/modal.js"></script> 

 
 
 <style type="text/css"> 
 
 @import "/facelet-sandbox/css/modal.css"; 
 
 </style> 

 
 
 <a4j:region id="stat1"> 
 
 <a4j:outputPanel id="list-body"> 
 
 <t:dataTable id="carIndex" 

 ... 
 </t:dataTable> 
 
 </a4j:outputPanel> 
 
 <ac:ajaxDataScroller id="scroll_1" 

 for="carList" 
 maxPages="9"> 
 </ac:ajaxDataScroller> 
 
 <a4j:status for="stat1" forceId="true" id="ajaxStatus"> 

 <f:facet name="start"> 
 <div id="loading-modal"></div> 
 </f:facet> 
 </a4j:status> 

 
 </a4j:region> 
 
 

 

Css Source

Some generic css and important background styles at bottom:

 
 

 
/**************************************************************/ 
/*Modal Window*/ 
 
#modal { 
 background-color: #eee; 
 padding: 10px; 

 border-bottom: 2px solid #666; 
 border-right: 2px solid #666; 
 } 
 

#modal-details { 
 font-size: 8px; /* originally 8px */ 
 padding-top: 4px; 
 } 

 
#modal-caption { 
 float: left; 
} 
 
#loadingMsg { 
 float: right; 

} 
 
#modal img { 
 border: none; 
 clear: both; 
} 
 
#overlay img { 

 border: none; 
} 
 
#overlay { 
 background-image: url(/facelet-sandbox/images/modal/overlay-black.png); 
} 

 
* html #overlay { 
 background-color: transparent; 
 background-image: url(blank.gif); 
 filter: progid:DXImageTransform.Microsoft.AlphaImageLoader(src="/facelet-sandbox/images/modal/overlay-black.png", sizingMethod="scale"); 

} 
 
/**************************************************************/

 

This is our end result when you rerender a component using A4J. Btw, (you can modify the AjaxAnywhere js to do the same thing)

My Jroller Blog Extreme Makeover

18 December 2006

Design |

I need a new design badly (the little British car in the tunnel is getting old, quick), and after coding for x number of months, I feel like my design skillz are getting a little stale. So here are the candidates for my new look.

Layout #1

Layout #2

Using Facelets TagHandlers and Adding multiple listeners

18 December 2006

Java |

ComponentHandler, HtmlComponentHandler, or TagHandler. So I think I finally have a handle on what each of these are used for. Okay the first 2 are easy, HtmlComponentHandler extends ComponentHandler. But what is a MetaRuleset and what can it do for my components? It looks to mee like it is just a method binding passthrough for the component when you call MetaRuleset.addRule(typeTagRule);?

TagHandler ended up saving the day for me, and after spending hours/days trying to get the first 2 to do what I was wanting, this one took me like 5 minutes. I was trying to add a handler to a component which turned out to be the wrong thing to do in facelets. Now, All one has to do is declare a tag in the *taglib.xml file and point it to the new handler class (as explained on Facelets docs).

    <tag> 
        <tag-name>sliderListener</tag-name> 
        <handler-class>com.halesconsulting.web.jsf.handler.SliderTagHandler</handler-class> 
    </tag> 

Next is defining the required and not-required attributes for your tag in the class.

  private final TagAttribute test; 
  private final TagAttribute var; 

  public SliderTagHandler(TagConfig config) { 
      super(config); 
 
      // helper method for getting a required attribute 
      this.test = this.getRequiredAttribute("type"); 

 
      // helper method 
      this.var = this.getAttribute("var"); 
  } 

Next, in the apply method, I was able to get this tags parent component instance (just like in JSP component development where you call UIComponentTag tag = UIComponentTag.getParentUIComponentTag(pageContext); It took me a while to figure out where I needed to do this, but after this worked, you should have seen the excitement! Nothing like figuring shit out on your own when no documentation could be found on what you are trying to do!

I had to add a HashMap to keep track of what listeners had already been added. Otherwise, each render added a new listener...

  /** 

   * Threadsafe Method for controlling evaluation of 
   * its child tags, represented by "nextHandler" 
   */ 
  public void apply(FaceletContext ctx, UIComponent parent) throws IOException, FacesException, ELException { 
 
      boolean b = this.test.getBoolean(ctx); 

 
      if (!addedMap.containsKey(test.getValue())){ 
          SliderSource sliderSource = (SliderSource)parent; 
          SliderListener listener = createSliderListener(test.getValue()); 
          addedMap.put(test.getValue(),true); 
          sliderSource.addSliderListener(listener); 
      } 
       

      if (this.var != null) { 
          ctx.setAttribute(var.getValue(ctx), new Boolean(b)); 
      } 
      if (b) { 
          this.nextHandler.apply(ctx, parent); 

      } 
  } 

I still need to do a little more digging on the details of the nextHandler stuff. But I was happy to get it working the "right way"

JSF Chart Creator - now with ImageMaps!

16 December 2006

Java |

I recently updated the JSF-Comp Chart Creator component to include image map support. All charts now have capabilties for custom links on each section of the chart. All customization can be handled through the tag atributes.

New attributes:

  • action
  • series
  • section

The usemap attribute must start with a # (i.e. usemap="#myMap"). For action, just input the page to link to, section and series are just parameters that are built into jfreeChart. I am currently working on drill downs, along with a few other attributes (like the abiltiy to set the range), for next release.

Usage

Besides the new attributes and an h:output tag for your imagemap string, there is nothing else you need to know apart from this documentation

Download the jar here


        <ad:chart id="chart2" 
                  datasource="#{chartCreator.cellBar}" 
                  type="bar" 
                  height="100" 

                  is3d="false" 
                  orientation="horizontal" 
                  width="300" 
                  antialias="true" 
                  title="" 

                  xlabel="" 
                  ylabel="" 
                  legend="false" 
                  usemap="#chart2_map" 
                  action="this.jsf" 

                  series="wes1" 
                  section="wes2" 
                  styleClass="wesChart"></ad:chart> 
        <h:outputText escape="false" value="#{chart1_map}"/> 



Maven 2 vs Ant - Which is better for commercial apps

10 December 2006

Java |

Currently I am working on a extreme RIA which is to use the code base of an existing project and rewrite were needed. Because of the strict time line, no one is attempting to rewrite the existing code base, and we are looking over problems that need to be fixed just to get things working.

However, we have made the appropriate steps to create a Maven archetype for the new part of the app, and to get the ball rolling away from the old ant build. What I'm wondering is:

  1. Is Maven really better suited for open source projects and not commercial?
  2. There are a ton of threads talking about how you have to be a Maven expert once the project grows past a certain point and something breaks.
  3. By googling "Maven vs. Ant" I find many threads but most are dated. I'm interested in how commercial projects are doing with the latest version of Maven today.

I came across a Selenium article on Matt Raible's blog that got the wheels turning. Since (it seems)everyone is moving towards Maven 2, will an existing ant project be better off ported to Maven?

Selenium is becoming fairly mainstream and now that Mavenium is up and coming it makes me wonder if Maven is really the way to go.

Ajax4Jsf vs AjaxAnywhere: The t:dataTable and t:dataScroller

07 December 2006

Java |

Submitting with Ajax4Jsf

On Dec 6, Ajax4Jsf released a maintenance release (ajax4jsf-1.0.4MR1.jar which fixed an IE javascript problem not in this post) - But the framework is still a little buggy dealing with the datascroller components. On a good note, Adrian Mitev gave his custom ajaxDataScroller to the A4J project and will hopefully get everything working in both browsers. ***UPDATE - Here is the latest version of the datascroller from Adrian. I had to rename the extension to .jar instead of .zip for upload reasons. If you have trouble extracting, just rename the file to .zip. Adrian says "Actually the attributes of ac:ajaxDataScroller tag differs from the attributes of t:dataScroller. You don't have paginatorMaxPages="9", the attribute is maxPages."

<a4j:form ajaxSubmit="true" reRender="carList,carIndex,scroll_1"> 
 
            <a4j:region id="stat1"> 
 
                <a4j:outputPanel id="list-body"> 
 
                    <t:dataTable id="carIndex"...> 
 
                    <t:dataTable id="carList"...> 
 
                </a4j:outputPanel> 
 
                <t:dataScroller id="scroll_1" 
                        for="carList" 
                        fastStep="10" 
                        pageCountVar="pageCount" 
                        pageIndexVar="pageIndex" 
                        styleClass="scroller" 
                        paginator="true" 
                        paginatorMaxPages="9" 
                        paginatorTableClass="paginator" 
                        paginatorActiveColumnStyle="font-weight:bold;" 
                        actionListener="#{inventoryList.scrollerAction}" 
                        > 
                </t:dataScroller> 
 
                <a4j:status for="stat1" forceId="true" id="ajaxStatus"...> 
 
             </a4j:region> 
 
 
        </a4j:form> 

The above code is functional in Firefox 1.5+ but not in IE 6+. The only bug in Firefox (that I've seen so far) is that a selected status/style on the page number link, once it has been clicked, does not appear. It looks like the component itself is not being reRendered, although it is specified in the a4j:form tag. Other than that, Sergey, Alex, and crew have been doing an awesome job answering posts and getting the maintenance releases out... keep em' coming guys!

The paging doesn't work at all in IE - it has to be something small...

Submitting with AjaxAnywhere

As much as I would love to stick with one ajax framework across the entire app, we have to have a fallback plan. AjaxAnywhere has been a life saver getting the Tomahawk components submitting. The only downfall with this framework is that you are limited no partial page updates, and nowhere near the capabilities/enhancements that A4J has...

The following code does the Ajax submit in both browser with all components working like they should. Using the A4J:status together with a custom "loading..." window with aa took some hackery, but I was able to get both working (in next post I will explain)

<h:form id="mainForm"> 
 
                <aa:zoneJSF id="dataTableZone"> 

                         
                <a4j:region id="stat1"> 
     
                <a4j:outputPanel id="list-body"> 
                <t:dataTable...> 
                </a4j:outputPanel> 

     
                        <a4j:status for="stat1" forceId="true" id="ajaxStatus"...> 
     
                 </a4j:region> 
     

                <t:dataScroller id="scroll_1"...> 
 
            </aa:zoneJSF> 
 
        </h:form> 
 

        <script type="text/JavaScript" src="/facelet-sandbox/aa.js"/> 
 
         <script type="text/JavaScript"> 
 
            ajaxAnywhere.getZonesToReload = function(url, submitButton) { 

                return 'dataTableZone'; 
            } 
 
            ajaxAnywhere.formName = 'mainForm'; 
            ajaxAnywhere.substituteFormSubmitFunction(); 
            ajaxAnywhere.substituteSubmitButtonsBehavior(true); 

           
        </script> 

One more thing, the reason I am nesting an a4j:outputPanel in the above code is for a4j:commandLinks inside the form. So far I haven't had any problems with both frameworks playing nicely together

JSF Component Library Integration

06 December 2006

JSF | Java |

Integrating multiple component libraries can provide a project many advantages but can also be a challenge to make all components live and work in harmony. This article explains how to integrate many popular component libraries into one app. Combining libraries gives developers an array of components to pick and choose from. But, knowing which components play well together and which ones don?t, will save you time and I will explain the pros and cons of each here. The following component libraries were used:


Libs

  • Myfaces 1.1.4
  • Tomahawk 1.1.4
  • Ajax4JSF 1.0.3
  • Trinidad m1 Nightly Build
  • IceFaces 1.0.1
  • Facelets 1.0.11

Environment

  • JDK 1.5 +
  • Jboss 4.0.4 (or Tomcat is better/lighter)
  • IntelliJ Idea

Software Needed

  • Subversion
  • CVS
  • Maven 2

It's worth the effort to go ahead and get yourself acquainted with downloading the source for most of your component libraries, starting with Myfaces. I use Tortoise SVN or you can download the binaries using the command line. Once you have Subversion setup, checkout Myfaces here. After that, this guide This will give you a quick how to on compiling the libraries with Maven 2. If you use IntelliJ Idea you can get a plugin that will generate your project files. This will allow you to edit the source and change things around if needed, it also helps when you are trying to follow this guide.

For the impatient, the short and sweet steps are:

  1. Download Maven 2 and add bin dir to path
  2. checkout code for project
  3. navigate to root dir (or dir with pom.xml file)
  4. run mvn install
  5. This will build the target directory for the project which will contain compiled jars, examples wars, etc.

Myfaces

Checkout: http://svn.apache.org/repos/asf/myfaces

Each servlet container has its own configuration in which details can be found here. Overall the latest version of Tomcat and Jboss had no major issues with the out-of-box Myfaces configuration. If you are integrating Myfaces with an existing JSF RI, there are steps with the ExtensionsFilter that must be taken located on the Myfaces wiki.

Viewing this up to date compatibility matrix, will ensure you are working with compatible libraries.

There are a number of performance settings you can make with Myfaces, but with integration of components being the focus for this article, performance tuning will be discussed in part 2 of this series.

Tomahawk

Checkout: Checkout: http://svn.apache.org/repos/asf/myfaces/tomahawk

Once you have the latest Tomahawk build checked out, you can find almost all of the Myfaces and Tomahawk configuration and performance settings in the sandbox/examples/src/main/webapp/WEB-INF/web.xml file. All of the settings are applicable to this article, and it is a great starting point that is well commented.

When using Facelets, each project requires its own tag library. Unfortunately Tomahawk does not include Facelet integration built into their jar(as of 1.1.4). This requires you to put together tomahawk.taglib.xml and point to it from settings in your web.xml.

<context-param>
<param-name>facelets.LIBRARIES</param-name>
<param-value>/WEB-INF/tomahawk.taglib.xml</param-value>
</context-param>

This provides pass-through getters and setters to the tomahawk library. You can write a *.taglib.xml for any library, but you may need to write a Facelets TagHandler.

Ajax4jsf

Checkout (use cvs): cvs -d :pserver:yourName@cvs.dev.java.net:/cvs checkout ajax4jsf

One of the largest hurdles with this library was integration with Trinidad. Trinidad and Ajax4JSF use their own ViewHandler with Facelets and both are very picky about how and where they are loaded.

Web.xml

<filter>
<display-name>Ajax4jsf Filter</display-name>
<filter-name>ajax4jsf</filter-name>
<filter-class>org.ajax4jsf.Filter</filter-class>
</filter>

<filter-mapping>
<filter-name>ajax4jsf</filter-name>
<servlet-name>FacesServlet</servlet-name>
</filter-mapping>

faces-config.xml

<application>
<default-render-kit-id>org.apache.myfaces.trinidad.core</default-render-kit-id>
<view-handler>org.ajax4jsf.framework.ajax.AjaxViewHandler</view-handler>
</application>

Initially I tried to use Neko HTML for the component XML rendering and had to abandon it because of one extra tag at the end of the response. Neko is known for not trying to "over" correct the code, but in this case it did not work. With the default Ajax4Jsf filter, you get Tidy cleaning up the response and that seemed to work just fine. Tidy is also configurable through a .properties file with various parser settings.

As of version 1.0.3, there have been many improvements and I was able to get everything working together from the settings above. This version also includes the integration jar for working with Trininad released after September 29, 2006.

One very nice debugging helper for this library is the logConsole div:

<div style="padding: 5px; overflow: auto; font-size: 9px; height: 150px; width: 100%;" id="logConsole"></div>

This allows you to see the entire Ajax request/response going and coming back from the server. One thing you may want to create is a Facelets debugging template and add this along with the facelets debugging options into it.

Trinidad

Checkout: http://svn.apache.org/repos/asf/incubator/adffaces

Here we have the basic settings for Trinidad to integrate with your application. Because we are integrating with Ajax4Jsf, Trinidad is the only ViewHandler defined in the web.xml. In the a4j example above you see how the ViewHandler for Ajax4Jsf is defined in the faces-config.xml. Again, if you are not using these two libraries together then you need to follow the documentation from the libraries corresponding websites.

Web.xml

<context-param>
<param-name>org.apache.myfaces.trinidad.ALTERNATE_VIEW_HANDLER</param-name>
<param-value>com.sun.facelets.FaceletViewHandler</param-value>
</context-param>

<filter>
<filter-name>trinidad</filter-name>
<filter-class>org.apache.myfaces.trinidad.webapp.TrinidadFilter</filter-class>
</filter>

<filter-mapping>
<filter-name>trinidad</filter-name>
<servlet-name>FacesServlet</servlet-name>
<dispatcher>REQUEST</dispatcher>
<dispatcher>FORWARD</dispatcher>
<dispatcher>INCLUDE</dispatcher>
</filter-mapping>

One important topic I would like to touch on is client-side state saving vs. server-side. Trinidad offers a unique strategy for JSF state saving which will allow tokens to be sent to the client allowing minimal performance drag. The default client-side state saving only saves a token to the client, and saves the real state in the HttpSession. MyFaces tells users to use server-side and Trinidad prefers client-side, but they are basically the same thing in terms of HttpSession. Also, failover is supported with the Trinidad state saving method.

As for components, Trinidad starts with more than 100 components which have already been documented and thoroughly tested. Now we have tags from 3-4 different libraries that overlap each other. We must decide which one to use where, why we are using them, and what is best for performance. Tag usage, along with state saving, will be discussed in part 2 of this series.

IceFaces

TODO - Update this section

**Note, since the writing of this article, Icefaces has been open sourced*** If you wish to make use of clustering and advanced asynchronous HTTP handling in a large-scale application, they want you to move up to the Enterprise Edition.

As of ICEfaces v1.0.1 release, they now have support for JSF integration. You can view configuration instructions here. In short, you can use the just-ice.jar, instead of the icefaces.jar, and use other JSF servlet mappings (ie. Faces Servlet) to handle non-ICEfaces pages. If you do this, you must use **only** standard JSF tags (f:) and ICEfaces tags (ice:) in you JSF pages.

ICEFaces doesn't have the same approach as ajax4jsf and DynaFaces have. You will have to follow their component-model to get the benefits of the Direct2Dom technology, so hooking up components of other libraries together with the ICEFaces components isn't possible (as of now), as they cannot re-render arbitrary components through their renderkit.

If you need to combine components from an open source library with IceFaces, one option is to use an iframe within an icefaces page. The iframe could point to the other JSF framework Servlet/ViewHandler. I haven't tried this yet myself, but according to the IceFaces support staff, it's worth a try.

For Facelets integration, along with the core jars, you will need icefaces-facelets.jar. There are minimal settings that take place for Facelet integration. The steps are located here

Facelets

The facelets ViewHandler configuration placement is critical to your application. If you are ONLY integrating Ajax4Jsf with Facelets, you should have you settings in web.xml as follows:

<context-param>
<param-name>org.ajax4jsf.VIEW_HANDLERS</param-name>
<param-value>com.sun.facelets.FaceletViewHandler</param-value>
</context-param>

You need the above defined only if using Ajax4Jsf along with all other libraries besides Trinidad. If using Trinidad along with Ajax4Jsf and Facelets then follow the steps from the Trinidad section above.

One quick performance tip that will impact the foundational templating is the StreamingAddResource.

By adding:

<context-param>
<param-name>org.apache.myfaces.ADD_RESOURCE_CLASS</param-name>
<param-value>org.apache.myfaces.component.html.util.StreamingAddResource</param-value>
</context-param>

...to the web.xml and using...

  • t:document as replacement for html
  • t:documentHead as replacement for head
  • t:documentBody as replacement for body

...this will allow the pages to be streamed which will result in faster page delivery.

For debugging Facelets, add the following to your web.xml:



<context-param>
<param-name>facelets.DEVELOPMENT</param-name>
<param-value>true</param-value>
</context-param>

Setting this to true will cause the FaceletViewHandler to print out debug information in an easy to use screen when an error occurs during the rendering process. Probably one of the coolest features for debugging is the tag. Of course you can?t have ?cool? without an expense, so be careful when using this option because of overhead. You can use the UIComponent rendered property to turn debugging on or off based on some expression. In this example, debugging is backed by an entry in the web.xml.

<ui:debug hotkey="d" rendered="#{initParam.debugMode}"/>

The debug tag will capture the component tree and variables when it is encoded, storing the data for retrieval later. You may launch the debug window at any time from your browser by pressing 'CTRL' + 'SHIFT' + 'D' (by default). Like I said earlier the best place to put this tag is in your site's main template, or in some kind of debugging template, where it can be enabled/disabled across your whole application.

Preformatting html code blocks

05 December 2006

util |

When the time comes to put html or xml settings as an example in your blog (or any html for that matter), this sed one-liner really helps out...

Replace the *** with an "&"... the page example won't render correctly if I use verbatim characters.

cat -v article.xhtml | sed -e "s/***lt;/\</g" -e "s/>/\***gt;/g" > article.code.xhtml