type=page
status=published
title=HTML5-Friendly Markup
next=jsf-el.html
prev=jsf-facelets008.html
~~~~~~
= HTML5-Friendly Markup


[[BABGECCJ]]

[[html5-friendly-markup]]
HTML5-Friendly Markup
---------------------

When you want to produce user interface features for which HTML does not
have its own elements, you can create a custom JavaServer Faces
component and insert it in your Facelets page. This mechanism can cause
a simple element to create complex web code. However, creating such a
component is a significant task (see link:jsf-custom.html#BNAVG[Chapter
15, "Creating Custom UI Components and Other Custom Objects"]).

HTML5 offers new elements and attributes that can make it unnecessary to
write your own components. It also provides many new capabilities for
existing components. JavaServer Faces technology supports HTML5 not by
introducing new UI components that imitate HTML5 ones but by allowing
you to use HTML5 markup directly. It also allows you to use JavaServer
Faces attributes within HTML5 elements. JavaServer Faces technology
support for HTML5 falls into two categories:

* Pass-through elements
* Pass-through attributes

The effect of the HTML5-friendly markup feature is to offer the Facelets
page author almost complete control over the rendered page output,
rather than having to pass this control off to component authors. You
can mix and match JavaServer Faces and HTML5 components and elements as
you see fit.

[[sthref33]]

[[using-pass-through-elements]]
Using Pass-Through Elements
~~~~~~~~~~~~~~~~~~~~~~~~~~~

Pass-through elements allow you to use HTML5 tags and attributes but to
treat them as equivalent to JavaServer Faces components associated with
a server-side `UIComponent` instance.

To make an element that is not a JavaServer Faces element a pass-through
element, specify at least one of its attributes using the
`http://xmlns.jcp.org/jsf` namespace. For example, the following code
declares the namespace with the short name `jsf`:

[source,oac_no_warn]
----
<html ... xmlns:jsf="http://xmlns.jcp.org/jsf"
...
    <input type="email" jsf:id="email" name="email"
           value="#{reservationBean.email}" required="required"/>
----

Here, the `jsf` prefix is placed on the `id` attribute so that the HTML5
input tag's attributes are treated as part of the Facelets page. This
means that, for example, you can use EL expressions to retrieve managed
bean properties.

link:#BABJADGH[Table 8-4] shows how pass-through elements are rendered
as Facelets tags. The JSF implementation uses the element name and the
identifying attribute to determine the corresponding Facelets tag that
will be used in the server-side processing. The browser, however,
interprets the markup that the page author has written.

[[sthref34]][[BABJADGH]]

*Table 8-4 How Facelets Renders HTML5 Elements*

[width="60%",cols="20%,20%,20%" ]
|=======================================================
|*HTML5 Element Name*|*Identifying Attribute*|*Facelets Tag*
|`a` |`jsf:action` |`h:commandLink`
|`a` |`jsf:actionListener` |`h:commandLink`
|`a` |`jsf:value` |`h:outputLink`
|`a` |`jsf:outcome` |`h:link`
|`body` | + |`h:body`
|`button` | + |`h:commandButton`
|`button` |`jsf:outcome` |`h:button`
|`form` | + |`h:form`
|`head` | + |`h:head`
|`img` | + |`h:graphicImage`
|`input` |`type="button"` |`h:commandButton`
|`input` |`type="checkbox"` |`h:selectBooleanCheckbox`
|`input` |`type="color"` |`h:inputText`
|`input` |`type="date"` |`h:inputText`
|`input` |`type="datetime"` |`h:inputText`
|`input` |`type="datetime-local"` |`h:inputText`
|`input` |`type="email"` |`h:inputText`
|`input` |`type="month"` |`h:inputText`
|`input` |`type="number"` |`h:inputText`
|`input` |`type="range"` |`h:inputText`
|`input` |`type="search"` |`h:inputText`
|`input` |`type="time"` |`h:inputText`
|`input` |`type="url"` |`h:inputText`
|`input` |`type="week"` |`h:inputText`
|`input` |`type="file"` |`h:inputFile`
|`input` |`type="hidden"` |`h:inputHidden`
|`input` |`type="password"` |`h:inputSecret`
|`input` |`type="reset"` |`h:commandButton`
|`input` |`type="submit"` |`h:commandButton`
|`input` |`type="*"` |`h:inputText`
|`label` | + |`h:outputLabel`
|`link` | + |`h:outputStylesheet`
|`script` | + |`h:outputScript`
|`select` |`multiple="*"` |`h:selectManyListbox`
|`select` | + |`h:selectOneListbox`
|`textarea` | + |`h:inputTextArea`
|=======================================================


[[sthref35]]

[[using-pass-through-attributes]]
Using Pass-Through Attributes
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

Pass-through attributes are the converse of pass-through elements. They
allow you to pass attributes that are not JavaServer Faces attributes
through to the browser without interpretation. If you specify a
pass-through attribute in a JavaServer Faces `UIComponent`, the
attribute name and value are passed straight through to the browser
without being interpreted by JavaServer Faces components or renderers.
There are several ways to specify pass-through attributes.

* Use the JavaServer Faces namespace for pass-through attributes to
prefix the attribute names within a JavaServer Faces component. For
example, the following code declares the namespace with the short name
`p`, then passes the `type`, `min`, `max`, `required`, and `title`
attributes through to the HTML5 `input` component:
+
[source,oac_no_warn]
----
<html ... xmlns:p="http://xmlns.jcp.org/jsf/passthrough"
...

<h:form prependId="false">
<h:inputText id="nights" p:type="number" value="#{bean.nights}"
             p:min="1" p:max="30" p:required="required"
             p:title="Enter a number between 1 and 30 inclusive.">
        ...
----
+
This will cause the following markup to be rendered (assuming that
`bean.nights` has a default value set to 1):
+
[source,oac_no_warn]
----
<input id="nights" type="number" value="1" min="1" max="30"
       required="required"
       title="Enter a number between 1 and 30 inclusive.">
----
* To pass a single attribute, nest the `f:passThroughAttribute` tag
within a component tag. For example:
+
[source,oac_no_warn]
----
<h:inputText value="#{user.email}">
    <f:passThroughAttribute name="type" value="email" />
</h:inputText>
----
+
This code would be rendered similarly to the following:
+
[source,oac_no_warn]
----
<input value="me@me.com" type="email" />
----
* To pass a group of attributes, nest the `f:passThroughAttributes` tag
within a component tag, specifying an EL value that must evaluate to a
`Map<String, Object>`. For example:
+
[source,oac_no_warn]
----
<h:inputText value="#{bean.nights">
    <f:passThroughAttributes value="#{bean.nameValuePairs}" />
</h:inputText>
----
+
If the bean used the following `Map` declaration and initialized the map
in the constructor as follows, the markup would be similar to the output
of the code that uses the pass-through attribute namespace:
+
[source,oac_no_warn]
----
private Map<String, Object> nameValuePairs;
...
public Bean() {
    this.nameValuePairs = new HashMap<>();
    this.nameValuePairs.put("type", "number");
    this.nameValuePairs.put("min", "1");
    this.nameValuePairs.put("max", "30");
    this.nameValuePairs.put("required", "required");
    this.nameValuePairs.put("title",
            "Enter a number between 1 and 4 inclusive.");
}
----

[[BABGGIAA]]

[[the-reservation-example-application]]
The reservation Example Application
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

The `reservation` example application provides a set of HTML5 `input`
elements of various types to simulate purchasing tickets for a
theatrical event. It consists of two Facelets pages, `reservation.xhtml`
and `confirmation.xhtml`, and a backing bean, `ReservationBean.java`.
The pages use both pass-through attributes and pass-through elements.

The source code for this application is in the
tut-install`/examples/web/jsf/reservation/` directory.

The following topics are addressed here:

* link:#BABGCAHH[The Facelets Pages for the reservation Application]
* link:#BABHFCCG[The Managed Bean for the reservation Application]
* link:#BABIHHGC[To Build, Package, and Deploy the reservation Example
Using NetBeans IDE]

[[BABGCAHH]]

[[the-facelets-pages-for-the-reservation-application]]
The Facelets Pages for the reservation Application
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

The first important feature of the Facelets pages for the `reservation`
application is the `DOCTYPE` header. Most Facelets pages in JavaServer
Faces applications refer to the XHTML DTD. The facelets pages for this
application begin simply with the following `DOCTYPE` header, which
indicates an HTML5 page:

[source,oac_no_warn]
----
<!DOCTYPE html>
----

The namespace declarations in the `html` element of the
`reservation.xhtml` page specify both the `jsf` and the `passthrough`
namespaces:

[source,oac_no_warn]
----
<html lang="en"
      xmlns="http://www.w3.org/1999/xhtml"
      xmlns:f="http://xmlns.jcp.org/jsf/core"
      xmlns:h="http://xmlns.jcp.org/jsf/html"
      xmlns:p="http://xmlns.jcp.org/jsf/passthrough"
      xmlns:jsf="http://xmlns.jcp.org/jsf">
----

Next, an empty `h:head` tag followed by an `h:outputStylesheet` tag
within the `h:body` tag illustrates the use of a relocatable resource
(as described in link:jsf-facelets007.html#BABHGBJI[Relocatable
Resources]):

[source,oac_no_warn]
----
<h:head>
</h:head>
<h:body>
    <h:outputStylesheet name="css/stylesheet.css" target="head"/>
----

The `reservation.xhtml` page uses pass-through elements for most of the
form fields on the page. This allows it to use some HTML5-specific
`input` element types, such as `date` and `email`. For example, the
following element renders both a date format and a calendar from which
you can choose a date. The `jsf` prefix on the `id` attribute makes the
element a pass-through one:

[source,oac_no_warn]
----
    <input type="date" jsf:id="date" name="date"
           value="#{reservationBean.date}" required="required"
           title="Enter or choose a date."/>
----

The field for the number of tickets, however, uses the
`h:passThroughAttributes` tag to pass a `Map` defined in the managed
bean. It also recalculates the total in response to a change in the
field:

[source,oac_no_warn]
----
    <h:inputText id="tickets" value="#{reservationBean.tickets}">
        <f:passThroughAttributes value="#{reservationBean.ticketAttrs}"/>
        <f:ajax event="change" render="total"
                listener="#{reservationBean.calculateTotal}"/>
    </h:inputText>
----

The field for the price specifies the `number` type as a pass-through
attribute of the `h:inputText` element, offering a range of four ticket
prices. Here, the `p` prefix on the HTML5 attributes passes them through
to the browser uninterpreted by the JavaServer Faces input component:

[source,oac_no_warn]
----
    <h:inputText id="price" p:type="number"
                 value="#{reservationBean.price}"
                 p:min="80" p:max="120"
                 p:step="20" p:required="required"
                 p:title="Enter a price: 80, 100, 120, or 140.">
        <f:ajax event="change" render="total"
                listener="#{reservationBean.calculateTotal}"/>
    </h:inputText>
----

The output of the `calculateTotal` method that is specified as the
listener for the Ajax event is rendered in the output element whose `id`
and `name` value is `total`. See link:jsf-ajax.html#GKIOW[Chapter 13,
"Using Ajax with JavaServer Faces Technology"], for more information.

The second Facelets page, `confirmation.xhtml`, uses a pass-through
`output` element to display the values entered by the user and provides
a Facelets `h:commandButton` tag to allow the user to return to the
`reservation.xhtml` page.

[[BABHFCCG]]

[[the-managed-bean-for-the-reservation-application]]
The Managed Bean for the reservation Application
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

The session-scoped managed bean for the reservation application,
`ReservationBean.java`, contains properties for all the elements on the
Facelets pages. It also contains two methods, `calculateTotal` and
`clear`, that act as listeners for Ajax events on the
`reservation.xhtml` page.

[[BABIHHGC]]

[[to-build-package-and-deploy-the-reservation-example-using-netbeans-ide]]
To Build, Package, and Deploy the reservation Example Using NetBeans IDE
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

1.  Make sure that GlassFish Server has been started (see
link:usingexamples002.html#BNADI[Starting and Stopping GlassFish
Server]).
2.  From the File menu, choose Open Project.
3.  In the Open Project dialog box, navigate to:
+
[source,oac_no_warn]
----
tut-install/examples/web/jsf
----
4.  Select the `reservation` folder.
5.  Click Open Project.
6.  In the Projects tab, right-click the `reservation` project and
select Build.
+
This option builds the example application and deploys it to your
GlassFish Server instance.

[[sthref36]]

[[to-build-package-and-deploy-the-reservation-example-using-maven]]
To Build, Package, and Deploy the reservation Example Using Maven
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

1.  Make sure that GlassFish Server has been started (see
link:usingexamples002.html#BNADI[Starting and Stopping GlassFish
Server]).
2.  In a terminal window, go to:
+
[source,oac_no_warn]
----
tut-install/examples/web/jsf/reservation/
----
3.  Enter the following command:
+
[source,oac_no_warn]
----
mvn install
----
+
This command builds and packages the application into a WAR file,
`reservation.war`, that is located in the `target` directory. It then
deploys the WAR file to your GlassFish Server instance.

[[sthref37]]

[[to-run-the-reservation-example]]
To Run the reservation Example
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

At the time of the publication of this tutorial, the browser that most
fully implements HTML5 is Google Chrome, and it is recommended that you
use it to run this example. Other browsers are catching up, however, and
may work equally well by the time you read this.

1.  Enter the following URL in your web browser:
+
[source,oac_no_warn]
----
http://localhost:8080/reservation
----
2.  Enter information in the fields of the `reservation.xhtml` page.
+
The Performance Date field has a date field with up and down arrows that
allow you to increment and decrement the month, day, and year as well as
a larger down arrow that brings up a date editor in calendar form.
+
The Number of Tickets and Ticket Price fields also have up and down
arrows that allow you to increment and decrement the values within the
allowed range and steps. The Estimated Total changes when you change
either of these two fields.
+
Email addresses and dates are checked for format, but not for validity
(you can make a reservation for a past date, for instance).
3.  Click Make Reservation to complete the reservation or Clear to
restore the fields to their default values.
4.  If you click Make Reservation, the `confirmation.xhtml` page
appears, displaying the submitted values.
+
Click Back to return to the `reservation.xhtml` page.
