232 // Interactive validation must be done before dispatching the submit event.
233 HTMLFormControlElement* submitElement = 0;
234 Node* targetNode = event->target()->toNode();
235 if (targetNode && targetNode->isElementNode()) {
236 Element* targetElement = static_cast<Element*>(targetNode);
237 if (targetElement->isFormControlElement())
238 submitElement = static_cast<HTMLFormControlElement*>(targetElement);
239 }
240 if (!noValidate() && (!submitElement || !submitElement->formNoValidate())) {
241 Vector<RefPtr<HTMLFormControlElement> > unhandledInvalidControls;
242 // If the form has invalid controls, abort submission.
243 if (!checkValidity(unhandledInvalidControls)) {
244 RefPtr<HTMLFormElement> protector(this);
245 // Focus on the first focusable control.
246 for (unsigned i = 0; i < unhandledInvalidControls.size(); ++i) {
247 HTMLFormControlElement* unhandled = unhandledInvalidControls[i].get();
248 ASSERT(unhandled->hasOneRef());
249 if (unhandled->isFocusable()) {
250 unhandled->scrollIntoViewIfNeeded(false);
251 // scrollIntoViewIfNeeded() dispatches events, so the state
252 // of 'unhandled' might be changed.
253 if (unhandled->isFocusable()) {
254 unhandled->focus();
255 break;
256 }
257 }
258 }
259 // Warn about all of unforcusable controls.
260 Frame* frame = document()->frame();
261 for (unsigned i = 0; frame && i < unhandledInvalidControls.size(); ++i) {
262 HTMLFormControlElement* unhandled = unhandledInvalidControls[i].get();
263 if (unhandled->isFocusable())
264 continue;
265 String message("An invalid form control with name='%name' is not focusable.");
266 message.replace("%name", unhandled->name());
267 frame->domWindow()->console()->addMessage(HTMLMessageSource, LogMessageType, ErrorMessageLevel, message, 0, document()->url().string());
268 }
269 m_insubmit = false;
270 return false;
271 }
272 }
273