    001// Copyright 2006-2013 The Apache Software Foundation
    002//
    003// Licensed under the Apache License, Version 2.0 (the "License");
    004// you may not use this file except in compliance with the License.
    005// You may obtain a copy of the License at
    006//
    007//     http://www.apache.org/licenses/LICENSE-2.0
    008//
    009// Unless required by applicable law or agreed to in writing, software
    010// distributed under the License is distributed on an "AS IS" BASIS,
    011// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    012// See the License for the specific language governing permissions and
    013// limitations under the License.
    014
    015package org.apache.tapestry5.corelib.components;
    016
    017import org.apache.tapestry5.*;
    018import org.apache.tapestry5.annotations.AfterRender;
    019import org.apache.tapestry5.annotations.BeginRender;
    020import org.apache.tapestry5.annotations.Mixin;
    021import org.apache.tapestry5.annotations.Parameter;
    022import org.apache.tapestry5.corelib.base.AbstractField;
    023import org.apache.tapestry5.corelib.mixins.RenderDisabled;
    024
    025/**
    026 * A Checkbox component is simply a &lt;input type="checkbox"&gt;.
    027 *
    028 * @tapestrydoc
    029 */
    030public class Checkbox extends AbstractField
    031{
    032    /**
    033     * The value to be read or updated. If not bound, the Checkbox will attempt to edit a property of its container
    034     * whose name matches the component's id.
    035     */
    036    @Parameter(required = true, autoconnect = true)
    037    private boolean value;
    038
    039    /**
    040     * The object that will perform input validation. The validate binding prefix is
    041     * generally used to provide this object in a declarative fashion.
    042     */
    043    @Parameter(defaultPrefix = BindingConstants.VALIDATE, allowNull = false)
    044    @SuppressWarnings("unchecked")
    045    private FieldValidator<Object> validate;
    046
    047    @SuppressWarnings("unused")
    048    @Mixin
    049    private RenderDisabled renderDisabled;
    050
    051    @BeginRender
    052    void begin(MarkupWriter writer)
    053    {
    054        String asSubmitted = validationTracker.getInput(this);
    055
    056        boolean checked = asSubmitted != null ? Boolean.parseBoolean(asSubmitted) : value;
    057
    058        writer.element("input", "type", "checkbox",
    059                "name", getControlName(),
    060                "id", getClientId(),
    061                "checked", checked ? "checked" : null);
    062
    063        putPropertyNameIntoBeanValidationContext("value");
    064
    065        validate.render(writer);
    066
    067        removePropertyNameFromBeanValidationContext();
    068
    069        resources.renderInformalParameters(writer);
    070
    071
    072        decorateInsideField();
    073    }
    074
    075    @AfterRender
    076    void after(MarkupWriter writer)
    077    {
    078        writer.end(); // input
    079    }
    080
    081    @Override
    082    protected void processSubmission(String controlName)
    083    {
    084        String postedValue = request.getParameter(controlName);
    085
    086        boolean translated = postedValue != null;
    087
    088        // record as "true" or "false"
    089        validationTracker.recordInput(this, Boolean.toString(translated));
    090
    091        putPropertyNameIntoBeanValidationContext("value");
    092        try
    093        {
    094            fieldValidationSupport.validate(translated, resources, validate);
    095
    096            value = translated;
    097        } catch (ValidationException ex)
    098        {
    099            validationTracker.recordError(this, ex.getMessage());
    100        }
    101        removePropertyNameFromBeanValidationContext();
    102    }
    103
    104    /**
    105     * Computes a default value for the "validate" parameter using
    106     * {@link org.apache.tapestry5.services.FieldValidatorDefaultSource}.
    107     */
    108    final Binding defaultValidate()
    109    {
    110        return defaultProvider.defaultValidatorBinding("value", resources);
    111    }
    112}