001// Copyright 2004, 2005 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.tapestry.form;
016
017import java.awt.Point;
018
019import org.apache.tapestry.IAsset;
020import org.apache.tapestry.IForm;
021import org.apache.tapestry.IMarkupWriter;
022import org.apache.tapestry.IRequestCycle;
023import org.apache.tapestry.Tapestry;
024
025/**
026 * Used to create an image button inside a {@link Form}. Although it is occasionally useful to know
027 * the {@link Point}on the image that was clicked (i.e., use the image as a kind of image map,
028 * which was the original intent of the HTML element), it is more commonly used to provide a graphic
029 * image for the user to click, rather than the rather plain &lt;input type=submit&gt;. [ <a
030 * href="../../../../../ComponentReference/ImageSubmit.html">Component Reference </a>]
031 * 
032 * @author Howard Lewis Ship
033 */
034
035public abstract class ImageSubmit extends Submit
036{
037    /**
038     * @see org.apache.tapestry.form.AbstractFormComponent#setName(org.apache.tapestry.IForm)
039     */
040    protected void setName(IForm form)
041    {
042        String nameOverride = getNameOverride();
043
044        setName((nameOverride == null) ? form.getElementId(this) : form.getElementId(this, nameOverride));
045    }
046
047    protected boolean isClicked(IRequestCycle cycle, String name)
048    {
049        String parameterName = name + ".x";
050
051        return (cycle.getParameter(parameterName) != null);
052    }
053    
054    protected void renderFormComponent(IMarkupWriter writer, IRequestCycle cycle)
055    {
056        boolean disabled = isDisabled();
057        IAsset disabledImage = getDisabledImage();
058
059        IAsset finalImage = (disabled && disabledImage != null) ? disabledImage : getImage();
060
061        String imageURL = finalImage.buildURL();
062
063        writer.beginEmpty("input");
064        writer.attribute("type", "image");
065        writer.attribute("name", getName());
066
067        if (disabled)
068            writer.attribute("disabled", "disabled");
069
070        // NN4 places a border unless you tell it otherwise.
071        // IE ignores the border attribute and never shows a border.
072
073        writer.attribute("border", 0);
074
075        writer.attribute("src", imageURL);
076
077        renderIdAttribute(writer, cycle);
078
079        renderInformalParameters(writer, cycle);
080
081        writer.closeTag();
082    }
083
084    void handleClick(IRequestCycle cycle, IForm form)
085    {
086        // The point parameter is not really used, unless the
087        // ImageButton is used for its original purpose (as a kind
088        // of image map). In modern usage, we only care about
089        // whether the user clicked on the image (and thus submitted
090        // the form), not where in the image the user actually clicked.
091
092        if (isParameterBound("point"))
093        {
094            int x = Integer.parseInt(cycle.getParameter(getName() + ".x"));
095            int y = Integer.parseInt(cycle.getParameter(getName() + ".y"));
096
097            setPoint(new Point(x, y));
098        }
099
100        super.handleClick(cycle, form);
101    }
102
103    /** parameter */
104    public abstract IAsset getDisabledImage();
105
106    /** parameter */
107    public abstract IAsset getImage();
108
109    /** parameter */
110    public abstract String getNameOverride();
111
112    /** parameter */
113    public abstract void setPoint(Point point);
114
115    protected void prepareForRender(IRequestCycle cycle)
116    {
117        super.prepareForRender(cycle);
118
119        if (getImage() == null)
120            throw Tapestry.createRequiredParameterException(this, "image");
121    }
122}