/
OutputLabel.java
71 lines (62 loc) · 3.04 KB
/
OutputLabel.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
/*
* Copyright 2017 OmniFaces
*
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
* an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
* specific language governing permissions and limitations under the License.
*/
package org.omnifaces.component.output;
import static java.lang.String.format;
import static org.omnifaces.util.Components.findComponentRelatively;
import static org.omnifaces.util.Components.getOptionalLabel;
import static org.omnifaces.util.Components.setLabel;
import static org.omnifaces.util.Utils.isEmpty;
import javax.el.ValueExpression;
import javax.faces.component.FacesComponent;
import javax.faces.component.UIComponent;
import javax.faces.component.html.HtmlOutputLabel;
import javax.faces.event.ComponentSystemEvent;
import javax.faces.event.PostRestoreStateEvent;
/**
* <p>
* The <code><o:outputLabel></code> is a component that extends the standard <code><h:outputLabel></code>
* with support for automatically setting its value as the label of the component identified by its <code>for</code>
* attribute (if any). This way there's no need to duplicate the very same label into the <code>label</code> attribute
* of the input component. After submitting the form without having entered a value, a validation message is posted that
* should contain the label printed before the input instead of some generated ID.
* <p>
* You can use it the same way as <code><h:outputLabel></code>, you only need to change <code>h:</code> into
* <code>o:</code>.
*
* @author Arjan Tijms
*/
@FacesComponent(OutputLabel.COMPONENT_TYPE)
public class OutputLabel extends HtmlOutputLabel {
public static final String COMPONENT_TYPE = "org.omnifaces.component.output.OutputLabel";
private static final String ERROR_FOR_COMPONENT_NOT_FOUND =
"A component with Id '%s' as specified by the for attribute of the OutputLabel with Id '%s' could not be found.";
@Override
public void processEvent(ComponentSystemEvent event) {
if (event instanceof PostRestoreStateEvent) {
String forValue = (String) getAttributes().get("for");
if (!isEmpty(forValue)) {
UIComponent forComponent = findComponentRelatively(this, forValue);
if (forComponent == null) {
throw new IllegalArgumentException(format(ERROR_FOR_COMPONENT_NOT_FOUND, forValue, getId()));
}
// To be sure, check if the target component doesn't have a label already. This
// is unlikely, since otherwise people have no need to use this outputLabel component
// but check to be sure.
if (getOptionalLabel(forComponent) == null) {
ValueExpression valueExpression = getValueExpression("value");
setLabel(forComponent, valueExpression != null ? valueExpression : getValue());
}
}
}
}
}