2 * Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserved.
3 * Copyright (C) 2010 Google Inc. All rights reserved.
4 * Copyright (C) 2012 Samsung Electronics. All rights reserved.
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Library General Public
8 * License as published by the Free Software Foundation; either
9 * version 2 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Library General Public License for more details.
16 * You should have received a copy of the GNU Library General Public License
17 * along with this library; see the file COPYING.LIB. If not, write to
18 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
19 * Boston, MA 02110-1301, USA.
24 #include "core/html/forms/ImageInputType.h"
26 #include "HTMLNames.h"
27 #include "InputTypeNames.h"
28 #include "core/events/MouseEvent.h"
29 #include "core/fetch/ImageResource.h"
30 #include "core/html/FormDataList.h"
31 #include "core/html/HTMLFormElement.h"
32 #include "core/html/HTMLImageLoader.h"
33 #include "core/html/HTMLInputElement.h"
34 #include "core/html/parser/HTMLParserIdioms.h"
35 #include "core/rendering/RenderImage.h"
36 #include "wtf/PassOwnPtr.h"
37 #include "wtf/text/StringBuilder.h"
41 using namespace HTMLNames;
43 inline ImageInputType::ImageInputType(HTMLInputElement& element)
44 : BaseButtonInputType(element)
48 PassRefPtrWillBeRawPtr<InputType> ImageInputType::create(HTMLInputElement& element)
50 return adoptRefWillBeNoop(new ImageInputType(element));
53 const AtomicString& ImageInputType::formControlType() const
55 return InputTypeNames::image;
58 bool ImageInputType::isFormDataAppendable() const
63 bool ImageInputType::appendFormData(FormDataList& encoding, bool) const
65 if (!element().isActivatedSubmit())
67 const AtomicString& name = element().name();
69 encoding.appendData("x", m_clickLocation.x());
70 encoding.appendData("y", m_clickLocation.y());
74 DEFINE_STATIC_LOCAL(String, dotXString, (".x"));
75 DEFINE_STATIC_LOCAL(String, dotYString, (".y"));
76 encoding.appendData(name + dotXString, m_clickLocation.x());
77 encoding.appendData(name + dotYString, m_clickLocation.y());
79 if (!element().value().isEmpty())
80 encoding.appendData(name, element().value());
84 String ImageInputType::resultForDialogSubmit() const
87 result.appendNumber(m_clickLocation.x());
89 result.appendNumber(m_clickLocation.y());
90 return result.toString();
93 bool ImageInputType::supportsValidation() const
98 static IntPoint extractClickLocation(Event* event)
100 if (!event->underlyingEvent() || !event->underlyingEvent()->isMouseEvent())
102 MouseEvent* mouseEvent = toMouseEvent(event->underlyingEvent());
103 if (mouseEvent->isSimulated())
105 return IntPoint(mouseEvent->offsetX(), mouseEvent->offsetY());
108 void ImageInputType::handleDOMActivateEvent(Event* event)
110 RefPtr<HTMLInputElement> element(this->element());
111 if (element->isDisabledFormControl() || !element->form())
113 element->setActivatedSubmit(true);
114 m_clickLocation = extractClickLocation(event);
115 element->form()->prepareForSubmission(event); // Event handlers can run.
116 element->setActivatedSubmit(false);
117 event->setDefaultHandled();
120 RenderObject* ImageInputType::createRenderer(RenderStyle*) const
122 RenderImage* image = new RenderImage(&element());
123 image->setImageResource(RenderImageResource::create());
127 void ImageInputType::altAttributeChanged()
129 RenderImage* image = toRenderImage(element().renderer());
132 image->updateAltText();
135 void ImageInputType::srcAttributeChanged()
137 if (!element().renderer())
139 element().imageLoader()->updateFromElementIgnoringPreviousError();
142 void ImageInputType::startResourceLoading()
144 BaseButtonInputType::startResourceLoading();
146 HTMLImageLoader* imageLoader = element().imageLoader();
147 imageLoader->updateFromElement();
149 RenderImage* renderer = toRenderImage(element().renderer());
153 RenderImageResource* imageResource = renderer->imageResource();
154 imageResource->setImageResource(imageLoader->image());
156 // If we have no image at all because we have no src attribute, set
157 // image height and width for the alt text instead.
158 if (!imageLoader->image() && !imageResource->cachedImage())
159 renderer->setImageSizeForAltText();
162 bool ImageInputType::shouldRespectAlignAttribute()
167 bool ImageInputType::canBeSuccessfulSubmitButton()
172 bool ImageInputType::isImageButton() const
177 bool ImageInputType::isEnumeratable()
182 bool ImageInputType::shouldRespectHeightAndWidthAttributes()
187 unsigned ImageInputType::height() const
189 RefPtr<HTMLInputElement> element(this->element());
191 if (!element->renderer()) {
192 // Check the attribute first for an explicit pixel value.
194 if (parseHTMLNonNegativeInteger(element->fastGetAttribute(heightAttr), height))
197 // If the image is available, use its height.
198 if (element->hasImageLoader()) {
199 HTMLImageLoader* imageLoader = element->imageLoader();
200 if (imageLoader->image())
201 return imageLoader->image()->imageSizeForRenderer(element->renderer(), 1).height();
205 element->document().updateLayout();
207 RenderBox* box = element->renderBox();
208 return box ? adjustForAbsoluteZoom(box->contentHeight(), box) : 0;
211 unsigned ImageInputType::width() const
213 RefPtr<HTMLInputElement> element(this->element());
215 if (!element->renderer()) {
216 // Check the attribute first for an explicit pixel value.
218 if (parseHTMLNonNegativeInteger(element->fastGetAttribute(widthAttr), width))
221 // If the image is available, use its width.
222 if (element->hasImageLoader()) {
223 HTMLImageLoader* imageLoader = element->imageLoader();
224 if (imageLoader->image())
225 return imageLoader->image()->imageSizeForRenderer(element->renderer(), 1).width();
229 element->document().updateLayout();
231 RenderBox* box = element->renderBox();
232 return box ? adjustForAbsoluteZoom(box->contentWidth(), box) : 0;
235 bool ImageInputType::hasLegalLinkAttribute(const QualifiedName& name) const
237 return name == srcAttr || BaseButtonInputType::hasLegalLinkAttribute(name);
240 const QualifiedName& ImageInputType::subResourceAttributeName() const
245 } // namespace WebCore