I have a "test.xhtml", based on a template:
<ui:composition xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html"
template="/templates/BasicTemplate.xhtml">
<f:loadBundle basename="label" var="label" />
...
<h:commandButton value="#{label.buttonname}" ...></h:commandButton>
...
The file "label.properties" is located in WEB-INF/classes.
But when I load it in my browser, there was no replacement, but instead of the expected name I got "label.buttonname" upon my button.
This problem only appears if I use it with templating.
What am I doing wrong?
I got it:
This is WRONG (!). LoadBudle is between composition and define tag.
<ui:composition xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html"
template="/templates/BasicTemplate.xhtml">
<f:loadBundle basename="label" var="label" /> <--- WRONG place!!!
<ui:define name="content">
<h:commandButton value="#{label.buttonname}" ...></h:commandButton>
</ui:define>
This is fine:
<ui:composition xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html"
template="/templates/BasicTemplate.xhtml">
<ui:define name="content">
<f:loadBundle basename="label" var="label" />
<h:commandButton value="#{label.buttonname}" ...></h:commandButton>
</ui:define>
Related
i'm trying to impelement google map in my project, so everything is fine in browser, but once i would generate it to apk, in the android device it will show a blank display. what would i do ?
androidManifest.xml:
<?xml version='1.0' encoding='utf-8'?>
<manifest android:hardwareAccelerated="true" android:versionCode="1" android:versionName="0.0.1" package="com.ionicframework.map678510" xmlns:android="http://schemas.android.com/apk/res/android">
<supports-screens android:anyDensity="true" android:largeScreens="true" android:normalScreens="true" android:resizeable="true" android:smallScreens="true" android:xlargeScreens="true" />
<uses-permission android:name="android.permission.INTERNET" />
<application android:hardwareAccelerated="true" android:icon="#mipmap/icon" android:label="#string/app_name" android:supportsRtl="true">
<activity android:configChanges="orientation|keyboardHidden|keyboard|screenSize|locale" android:label="#string/activity_name" android:launchMode="singleTop" android:name="MainActivity" android:theme="#android:style/Theme.DeviceDefault.NoActionBar" android:windowSoftInputMode="adjustResize">
<intent-filter android:label="#string/launcher_name">
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
<uses-sdk android:minSdkVersion="16" android:targetSdkVersion="25" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-feature android:name="android.hardware.location.gps" />
</manifest>
config.xml :
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<widget id="com.ionicframework.map678510" version="0.0.1" xmlns="http://www.w3.org/ns/widgets" xmlns:cdv="http://cordova.apache.org/ns/1.0">
<name>map</name>
<description>An awesome Ionic/Cordova app.</description>
<author email="hi#ionicframework" href="http://ionicframework.com/">Ionic Framework Team</author>
<content src="index.html"/>
<access origin="*"/>
<allow-navigation href="http://ionic.local/*"/>
<allow-intent href="http://*/*"/>
<allow-intent href="https://*/*"/>
<allow-intent href="tel:*"/>
<allow-intent href="sms:*"/>
<allow-intent href="mailto:*"/>
<allow-intent href="geo:*"/>
<platform name="android">
<allow-intent href="market:*"/>
</platform>
<platform name="ios">
<allow-intent href="itms:*"/>
<allow-intent href="itms-apps:*"/>
</platform>
<preference name="webviewbounce" value="false"/>
<preference name="UIWebViewBounce" value="false"/>
<preference name="DisallowOverscroll" value="true"/>
<preference name="android-minSdkVersion" value="16"/>
<preference name="BackupWebStorage" value="none"/>
<preference name="SplashMaintainAspectRatio" value="true"/>
<preference name="FadeSplashScreenDuration" value="300"/>
<preference name="SplashShowOnlyFirstTime" value="false"/>
<feature name="StatusBar">
<param name="ios-package" onload="true" value="CDVStatusBar"/>
</feature>
<plugin name="ionic-plugin-keyboard" spec="~2.2.1"/>
<plugin name="cordova-plugin-whitelist" spec="1.3.1"/>
<plugin name="cordova-plugin-console" spec="1.0.5"/>
<plugin name="cordova-plugin-statusbar" spec="2.2.1"/>
<plugin name="cordova-plugin-device" spec="1.1.4"/>
<plugin name="cordova-plugin-splashscreen" spec="~4.0.1"/>
</widget>
index.html:
<html lang="en" dir="ltr">
<head>
<meta charset="UTF-8">
<title>Ionic App</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, user-scalable=no">
<meta name="format-detection" content="telephone=no">
<meta name="msapplication-tap-highlight" content="no">
<link rel="icon" type="image/x-icon" href="assets/icon/favicon.ico">
<link rel="manifest" href="manifest.json">
<meta name="theme-color" content="#4e8ef7">
<script async defer src="https://maps.googleapis.com/maps/api/js?key=AIzaSyCcrLbMklPcdfCJmCVNDBR-o3c5x6zF7ck&callback="
type="text/javascript"></script>
<!-- cordova.js required for cordova apps -->
<script src="cordova.js"></script>
<!-- un-comment this code to enable service worker
<script>
if ('serviceWorker' in navigator) {
navigator.serviceWorker.register('service-worker.js')
.then(() => console.log('service worker installed'))
.catch(err => console.log('Error', err));
}
</script>-->
<link href="build/main.css" rel="stylesheet">
</head>
<body>
<!-- Ionic's root component and where the app will load -->
<ion-app></ion-app>
<!-- The polyfills js is generated during the build process -->
<script src="build/polyfills.js"></script>
<!-- The bundle js is generated during the build process -->
<script src="build/main.js"></script>
</body>
</html>
In JSF using PrimeFaces and Templates. none of my PrimeFaces effects are working when I place the code in .
Tried different primeface components-> Dialog, OverlayPanel, Expansion.....
when I write the same code (everything in one XHTML) without templates, it works fine.
Please help me here to come out of this situation.
Here is my template.xhtml
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
`"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">`
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:p="http://primefaces.org/ui"
xmlns:f="http://java.sun.com/jsf/core">
<h:head>
<h:outputStylesheet library="css" name="table-style.css" />
<p:ajaxStatus onstart="statusDialog.show();"
onsuccess="statusDialog.hide();" />
</h:head>
<h:body onload="statusDialog.hide();">
<div id="page">
<p:layout fullPage="true" resizeTitle="resize"
style="background-color:#F03D0C;">
<div id="header">
<p:layoutUnit position="north" size="75" id="north"
style="background-color:#F03D0C;">
<ui:include src="header.xhtml" />
</p:layoutUnit>
</div>
<div id="center">
<p:layoutUnit styleClass="layoutUnitCenter" position="center">
<h:form id="mainForm">
<p:messages autoUpdate="true" id="msgs" showDetail="true"
showSummary="true" />
<ui:insert name="content" />
<ui:include src="menu.xhtml" />
</h:form>
</p:layoutUnit>
</div>
<div id="footer">
<p:layoutUnit position="south" resizable="true" id="south">
<ui:include src="footer.xhtml" />
</p:layoutUnit>
</div>
</p:layout>
</div>
And here is my content xhtml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:p="http://primefaces.org/ui">
<h:body>
<ui:composition template="/templates/template.xhtml">
<ui:define name="content">
<h:form id="incidentForm">
<p:dataTable var="incdData" value="#{incidentDashboardView.incLst}"
styleClass="ui-datatable-data">
<f:facet name="header">Expand rows to see detailed information</f:facet>
<p:column style="width:16px">
<p:rowToggler />
</p:column>
<p:column headerText="Application"
sortBy="#{incdData.applicationName}">
<h:outputLink value="#{incdData.iteraUrl}">
<h:outputText value="#{incdData.applicationName}" />
</h:outputLink>
</p:column>
<p:column headerText="Total Ticket"
sortBy="#{incdData.totalTicket}">
<h:outputText value="#{incdData.totalTicket}" />
</p:column>
<p:column headerText="Assigned" sortBy="#{incdData.assignedTicket}">
<h:outputText value="#{incdData.assignedTicket}" />
</p:column>
<p:column headerText="InProgress"
sortBy="#{incdData.inProgressTicket}">
<h:outputText value="#{incdData.inProgressTicket}" />
</p:column>
<p:column headerText="Pending" sortBy="#{incdData.pendingTicket}">
<h:outputText value="#{incdData.pendingTicket}" />
</p:column>
<p:column headerText="Closed" sortBy="#{incdData.closedTicket}">
<h:outputText value="#{incdData.closedTicket}" />
</p:column>
<p:rowExpansion>
<p:panelGrid columns="2" columnClasses="label,value"
style="width:300px">
<p:dataTable var="incdAppDetailData"
value="#{incdData.incidentData}" styleClass="ui-datatable-data">
<p:columnGroup type="header">
<p:row>
<p:column headerText="Application"
sortBy="#{incdAppDetailData.applicationName}" />
<p:column headerText="Ticket"
sortBy="#{incdAppDetailData.incidentID}" />
<p:column headerText="Status"
sortBy="#{incdAppDetailData.status}" />
<p:column headerText="Reported Date"
sortBy="#{incdAppDetailData.reportedDate}" />
</p:row>
</p:columnGroup>
<p:column>
<h:outputText value="#{incdAppDetailData.applicationName}" />
</p:column>
<p:column>
<h:outputText value="#{incdAppDetailData.incidentID}" />
</p:column>
<p:column>
<h:outputText value="#{incdAppDetailData.status}" />
</p:column>
<p:column>
<h:outputText value="#{incdAppDetailData.reportedDate}" />
</p:column>
</p:dataTable>
</p:panelGrid>
</p:rowExpansion>
</p:dataTable>
</h:form>
</ui:define>
</ui:composition>
How could I reuse the included jsf template that would display more/less data
For example I have main.xhtml which includes the child.xhtml
child.xhtml as below
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:f="http://java.sun.com/jsf/core" xmlns:h="http://java.sun.com/jsf/html" xmlns:rich="http://richfaces.org/rich"
xmlns:a4j="http://richfaces.org/a4j" xmlns:c="http://java.sun.com/jstl/core" xmlns:s="http://jboss.com/products/seam/taglib">
<body>
<h:outputText value="One"></h:outputText>
<h:outputText value="Two"></h:outputText>
<h:outputText value="Three"></h:outputText>
<h:outputText value="Four"></h:outputText>
</body>
</html>
The current implementation of child.xhtml displays "One","Two","Three" and "Four". I want to include the above child.xhtml somewhere else where it should only display "Two" and "Four".
First of all, this is not a valid include file syntax. You're duplicating XML prolog, HTML doctype, <html> and <body> tags. This would only end up as illegal HTML syntax in the final output in webbrowser.
Fix it accordingly:
<ui:composition
xmlns="http://www.w3.org/1999/xhtml"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:ui="http://java.sun.com/jsf/facelets"
>
<h:outputText value="One" />
<h:outputText value="Two" />
<h:outputText value="Three" />
<h:outputText value="Four" />
</ui:composition>
See also:
How to include another XHTML in XHTML using JSF 2.0 Facelets?
Coming back to your concrete question, in order to conditionally render the components, just make use of rendered attribute. You can parameterize it by passing an <ui:param> to <ui:include>.
E.g.
<ui:composition
xmlns="http://www.w3.org/1999/xhtml"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:ui="http://java.sun.com/jsf/facelets"
>
<h:outputText value="One" rendered="#{empty hide or not hide}" />
<h:outputText value="Two" />
<h:outputText value="Three" rendered="#{empty hide or not hide}" />
<h:outputText value="Four" />
</ui:composition>
which can be used as
<ui:include src="/WEB-INF/includes/client.xhtml">
<ui:param name="hide" value="#{true}" />
</ui:include>
When <ui:param name="hide"> is omitted, or its value is not true, then they will be shown.
I'm a long time JSP user but facelets newbie and am stuck on what I thought would be a really simple task.
How can I wrap optional template content in a div tag?
For example given the following simplified template:
<?xml version='1.0' encoding='UTF-8' ?>
<html xml:lang="en" lang="en"
xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:h="http://java.sun.com/jsf/html">
<h:head>
<!-- head stuff here -->
</h:head>
<h:body>
<!-- main body stuff here -->
<div class="border-box">
<ui:insert name="optional" />
</div>
</h:body>
</html>
If I use this template without defining the optional content I'll get an unwanted empty box.
I've searched for a solution and found the same question posed a few times but no real answer.
Can anyone help me out? This seems to me to be quite a reasonable thing to want to do with a templating system but it's got me stumped.
Thanks mael, ui:fragment seems to be the way to go when the content will fit in a ui:param value attribute but I'm going with your first suggestion. I will template-ize the wrapper though with a ui:decorate.
Page template:
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html
PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xml:lang="en" lang="en"
xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:h="http://java.sun.com/jsf/html">
<h:head>
<!-- head stuff here -->
</h:head>
<h:body>
<!-- main body stuff here -->
<ui:insert name="optional" />
</h:body>
</html>
Wrapper template:
<?xml version='1.0' encoding='UTF-8' ?>
<ui:composition
xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets">
<div class="border-box">
<ui:insert />
</div>
</ui:composition>
Invocation:
<?xml version='1.0' encoding='UTF-8' ?>
<ui:composition
xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
template="page.xhtml">
<!-- other ui:defines -->
<ui:define name="optional">
<ui:decorate template="wrapper.xhtml">
<!-- optional content -->
</ui:decorate>
</ui:define>
</ui:composition>
Just delete the div and make something like this in the page that uses your template:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets">
<h:head />
<body>
<ui:composition template="template.xhtml">
<ui:define name="optional">
<div class="border-box">
<!-- Content here -->
</div>
</ui:define>
</ui:composition>
</body>
</html>
On a Facelets page I travel a list to display data in a p:dataTable (a PrimeFaces component).
This list itself contains another list that I travel using a c:forEach (JSTL).
The problem is that the data for the list that c:forEach should handle does not appear. When I access a specific element it works well, but not in a c:forEach.
Is it not possible to use an inner loop variable embedded in another loop?
Here's the page's code:
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:p="http://primefaces.org/ui"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:c="http://java.sun.com/jsp/jstl/core">
<body>
<ui:composition template="./template_utilisateur.xhtml">
<ui:define name="content">
<h:form prependId="false" id="form">
<p:growl id="growl" showDetail="true"/>
<p:dataTable id="carsTable" var="car" value="#{histCommController.lc}" rowKey="#{car.id}"
selectionMode="single" >
<f:facet name="header">
Expand rows to see detailed information
</f:facet>
<p:column style="width:4%">
<p:rowToggler/>
</p:column>
<p:column style="width:48%">
<f:facet name="header">
id
</f:facet>
<h:outputText value="#{car.id}" />
</p:column>
<p:column style="width:48%">
<f:facet name="header">
date envoi
</f:facet>
<h:outputText value="#{car.dateEnvoi}" />
</p:column>
<p:rowExpansion id="expanssion">
<h:panelGrid id="display" columns="2" cellpadding="4" style="width:300px;"
styleClass=" ui-widget-content grid">
<h:outputText value="Model:" />
<h:outputText value="#{car.id}" />
<h:outputText value="Year:" />
<h:outputText value="#{car.etat}" />
<h:outputText value="Manufacturer:" />
<h:outputText value="#{car.dateEnvoi}" />
<h:outputText value="Color:" />
<h:outputText value="#{car.dateLivraisonRecommande}" />
<h:outputText value="Fichiers : " />
<h:outputText value="::::::::::::" />
<h:outputText value="Fichiers 1 : " />
<h:outputText value="#{car.listFichiers.get(0).nom}" />
<c:forEach var="jjjjj" items="#{car.listFichiers}">
<h:outputText value="nom fichier 1 : " />
<h:outputText value="#{jjjjj.nom}" />
</c:forEach>
</h:panelGrid>
</p:rowExpansion>
</p:dataTable>
</h:form>
</ui:define>
</ui:composition>
</body>
</html>
The problem occurs because you are mixing so-called build-time and render-time constructs.
build-time happens first, and everything that happens there can not make use of things that don't exist until render-time, which happens after.
In your case, the JSTL forEach is build-time, while the car var is made available by the render-time dataTable. The solution is to use a render-time construct for the inner looping. The best candidate for this is ui:repeat.
See also
Beware the Difference Between Build-Time and Render-Time Tags in Facelets