Отображение форм только для чтения (значения отображаются как текст вместо отключенных элементов управления вводом) с JSF?

У меня есть форма ввода данных, в которой пользователь вводит множество данных. Когда пользователь приходит на страницу для просмотра существующих данных, страница должна отображаться в режиме только для чтения (все значения, показанные в виде текста), когда он нажимает кнопку "Изменить", должна отображаться нормальная форма со всеми элементами управления вводом, чтобы пользователь мог изменять и сохранять данные.

Мы используем JSF 2.0 с библиотекой PrimeFaces. Для текстового поля и текстовой области легко достичь вышеуказанного поведения, но не для элементов управления Checkbox, multi-select, radio,...... Есть ли какой-либо простой способ достичь вышеуказанного поведения, а не писать собственный код (который может работать во множестве строк, тем самым делая код bean уродливым)

Спасибо за вашу помощь...

Ответ 1

Я не уверен, почему вы думаете, что для этого вам нужен дополнительный код bean. У вас уже есть все необходимые значения в базе bean. Ваша проблема больше в представлении этих ценностей. Просто покажите их в нужном формате, написав соответственно код вида. Возможно, вы слишком сильно думали об этом.

Вместо флажка select boolean вы можете отобразить, например, значение "Да" или "Нет".

<h:selectBooleanCheckbox value="#{bean.checked}" rendered="#{bean.edit}" />
<h:outputText value="#{bean.checked ? 'Yes' : 'No'}" rendered="#{not bean.edit}" />

Вместо выбранного меню/радио вы можете просто отобразить значение в тексте вывода.

<h:selectOneMenu value="#{bean.selectedItem}" rendered="#{bean.edit}">
    <f:selectItems value="#{data.availableItems}" />
</h:selectOneMenu>
<h:outputText value="#{bean.selectedItem}" rendered="#{not bean.edit}" />

Вместо флажка select many listbox/check вы можете просто отобразить, например, все значения, разделенные запятой в цикле.

<h:selectManyListbox value="#{bean.selectedItems}" rendered="#{bean.edit}">
    <f:selectItems value="#{data.availableItems}" />
</h:selectManyListbox>
<h:panelGroup rendered="#{not bean.edit}">
    <ui:repeat value="#{bean.selectedItems}" var="selectedItem" varStatus="loop">
        #{selectedItem}#{not loop.last ? ', ' : ''}
    </ui:repeat>
</h:panelGroup>

Вы можете обернуть все это в файл тега или композит, чтобы свести к минимуму повторение шаблона и кода.

Ответ 2

Я сделал это в своем последнем проекте, используя составные компоненты, которые имеют атрибут предварительного просмотра, а в реализации я визуализую текст, когда этот атрибут является истинным, и реальным (редактированием), когда атрибут является ложным. Для флажка в режиме предварительного просмотра вы можете показать флажок самостоятельно, но отключен, для радио - показать выбранный элемент.

Библиотека MyFaces Tomahawk [1] содержит расширенную версию стандартных компонентов, которая добавляет для этой цели атрибут displayValueOnly. Это может помочь вам (я не использовал их).

[1] - http://myfaces.apache.org/tomahawk-project/tomahawk20/index.html