5ad452182405554f2dd475a418a3f3af76cf4106
[WebKit-https.git] / WebKitTools / DumpRenderTree / qt / jsobjects.cpp
1 /*
2  * Copyright (C) 2006 Trolltech ASA
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  *
8  * 1.  Redistributions of source code must retain the above copyright
9  *     notice, this list of conditions and the following disclaimer.
10  * 2.  Redistributions in binary form must reproduce the above copyright
11  *     notice, this list of conditions and the following disclaimer in the
12  *     documentation and/or other materials provided with the distribution.
13  * 3.  Neither the name of Apple Computer, Inc. ("Apple") nor the names of
14  *     its contributors may be used to endorse or promote products derived
15  *     from this software without specific prior written permission.
16  *
17  * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
18  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
19  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
20  * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
21  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
22  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
23  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
24  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27  */
28 #include <jsobjects.h>
29 #include <qwebpage.h>
30 #include <qwebframe.h>
31 #include <qevent.h>
32 #include <qapplication.h>
33 #include <qevent.h>
34
35 #include "DumpRenderTree.h"
36 extern void qt_dump_editing_callbacks(bool b);
37
38 LayoutTestController::LayoutTestController(WebCore::DumpRenderTree *drt)
39     : QObject()
40     , m_drt(drt)
41 {
42     m_timeoutTimer = 0;
43     reset();
44 }
45
46 void LayoutTestController::reset()
47 {
48     m_isLoading = true;
49     m_textDump = false;
50     m_dumpChildrenAsText = false;
51     m_canOpenWindows = false;
52     m_waitForDone = false;
53     m_dumpTitleChanges = false;
54     if (m_timeoutTimer) {
55         killTimer(m_timeoutTimer);
56         m_timeoutTimer = 0;
57     }
58     m_topLoadingFrame = 0;
59     qt_dump_editing_callbacks(false);
60 }
61
62 void LayoutTestController::maybeDump(bool ok)
63 {
64     QWebFrame *frame = qobject_cast<QWebFrame*>(sender());
65     if (frame != m_topLoadingFrame)
66         return;
67
68     m_topLoadingFrame = 0;
69
70     if (!shouldWaitUntilDone()) {
71         emit done();
72         m_isLoading = false;
73     }
74 }
75
76 void LayoutTestController::waitUntilDone()
77 {
78     //qDebug() << ">>>>waitForDone";
79     m_waitForDone = true;
80     m_timeoutTimer = startTimer(5000);
81 }
82
83 void LayoutTestController::notifyDone()
84 {
85     //qDebug() << ">>>>notifyDone";
86     if (!m_timeoutTimer)
87         return;
88     killTimer(m_timeoutTimer);
89     m_timeoutTimer = 0;
90     emit done();
91     m_isLoading = false;
92 }
93
94 int LayoutTestController::windowCount()
95 {
96     return m_drt->windowCount();
97 }
98
99 void LayoutTestController::clearBackForwardList()
100 {
101     m_drt->webPage()->history().clear();
102 }
103
104
105 void LayoutTestController::dumpEditingCallbacks()
106 {
107     qDebug() << ">>>dumpEditingCallbacks";
108     qt_dump_editing_callbacks(true);
109 }
110
111 void LayoutTestController::queueReload()
112 {
113     //qDebug() << ">>>queueReload";
114 }
115
116 void LayoutTestController::provisionalLoad()
117 {
118     QWebFrame *frame = qobject_cast<QWebFrame*>(sender());
119     if (!m_topLoadingFrame && m_isLoading)
120         m_topLoadingFrame = frame;
121 }
122
123 void LayoutTestController::timerEvent(QTimerEvent *)
124 {
125     qDebug() << ">>>>>>>>>>>>> timeout";
126     notifyDone();
127 }
128
129 QString LayoutTestController::encodeHostName(const QString &host)
130 {
131     QString encoded = QString::fromLatin1(QUrl::toAce(host + QLatin1String(".no")));
132     encoded.truncate(encoded.length() - 3); // strip .no
133     return encoded;
134 }
135
136 QString LayoutTestController::decodeHostName(const QString &host)
137 {
138     QString decoded = QUrl::fromAce(host.toLatin1() + QByteArray(".no"));
139     decoded.truncate(decoded.length() - 3);
140     return decoded;
141 }
142
143
144 EventSender::EventSender(QWebPage *parent)
145     : QObject(parent)
146 {
147     m_page = parent;
148 }
149
150 void EventSender::mouseDown()
151 {
152 //     qDebug() << "EventSender::mouseDown" << frame;
153     QMouseEvent event(QEvent::MouseButtonPress, m_mousePos, Qt::LeftButton, Qt::LeftButton, Qt::NoModifier);
154     QApplication::sendEvent(m_page, &event);
155 }
156
157 void EventSender::mouseUp()
158 {
159 //     qDebug() << "EventSender::mouseUp" << frame;
160     QMouseEvent event(QEvent::MouseButtonRelease, m_mousePos, Qt::LeftButton, Qt::LeftButton, Qt::NoModifier);
161     QApplication::sendEvent(m_page, &event);
162 }
163
164 void EventSender::mouseMoveTo(int x, int y)
165 {
166 //     qDebug() << "EventSender::mouseMoveTo" << x << y;
167     m_mousePos = QPoint(x, y);
168     QMouseEvent event(QEvent::MouseMove, m_mousePos, Qt::NoButton, Qt::NoButton, Qt::NoModifier);
169     QApplication::sendEvent(m_page, &event);
170 }
171
172 void EventSender::leapForward(int ms)
173 {
174     m_timeLeap += ms;
175     qDebug() << "EventSender::leapForward" << ms;
176 }
177
178 void EventSender::keyDown(const QString &string, const QStringList &modifiers)
179 {
180     QString s = string;
181     Qt::KeyboardModifiers modifs = 0;
182     for (int i = 0; i < modifiers.size(); ++i) {
183         const QString &m = modifiers.at(i);
184         if (m == "ctrlKey")
185             modifs |= Qt::ControlModifier;
186         else if (m == "shiftKey")
187             modifs |= Qt::ShiftModifier;
188         else if (m == "altKey")
189             modifs |= Qt::AltModifier;
190         else if (m == "metaKey")
191             modifs |= Qt::MetaModifier;
192     }
193     int code = 0;
194     if (string.length() == 1) {
195         code = string.unicode()->unicode();
196         qDebug() << ">>>>>>>>> keyDown" << code << (char)code;
197         // map special keycodes used by the tests to something that works for Qt/X11
198         if (code == '\t') {
199             code = Qt::Key_Tab;
200             if (modifs == Qt::ShiftModifier)
201                 code = Qt::Key_Backtab;
202             s = QString();
203         } else if (code == 127) {
204             code = Qt::Key_Backspace;
205             if (modifs == Qt::AltModifier)
206                 modifs = Qt::ControlModifier;
207             s = QString();
208         } else if (code == 'o' && modifs == Qt::ControlModifier) {
209             s = QLatin1String("\n");
210             code = '\n';
211             modifs = 0;
212         } else if (code == 'y' && modifs == Qt::ControlModifier) {
213             s = QLatin1String("c");
214             code = 'c';
215         } else if (code == 'k' && modifs == Qt::ControlModifier) {
216             s = QLatin1String("x");
217             code = 'x';
218         } else if (code == 'a' && modifs == Qt::ControlModifier) {
219             s = QString();
220             code = Qt::Key_Home;
221             modifs = 0;
222         } else if (code == 0xf702) {
223             s = QString();
224             code = Qt::Key_Left;
225             if (modifs & Qt::MetaModifier) {
226                 code = Qt::Key_Home;
227                 modifs &= ~Qt::MetaModifier;
228             }
229         } else if (code == 0xf703) {
230             s = QString();
231             code = Qt::Key_Right;
232             if (modifs & Qt::MetaModifier) {
233                 code = Qt::Key_End;
234                 modifs &= ~Qt::MetaModifier;
235             }
236         } else if (code == 'a' && modifs == Qt::ControlModifier) {
237             s = QString();
238             code = Qt::Key_Home;
239             modifs = 0;
240         } else {
241             code = string.unicode()->toUpper().unicode();
242         }
243     }
244     QKeyEvent event(QEvent::KeyPress, code, modifs, s);
245     QApplication::sendEvent(m_page, &event);
246 }
247
248 QWebFrame *EventSender::frameUnderMouse() const
249 {
250     QWebFrame *frame = m_page->mainFrame();
251
252 redo:
253     QList<QWebFrame*> children = frame->childFrames();
254     for (int i = 0; i < children.size(); ++i) {
255         if (children.at(i)->geometry().contains(m_mousePos)) {
256             frame = children.at(i);
257             goto redo;
258         }
259     }
260     if (frame->geometry().contains(m_mousePos))
261         return frame;
262     return 0;
263 }
264
265
266 TextInputController::TextInputController(QWebPage *parent)
267     : QObject(parent)
268 {
269 }
270
271 void TextInputController::doCommand(const QString &command)
272 {
273     Qt::KeyboardModifiers modifiers = Qt::NoModifier;
274     int keycode = 0;
275     if (command == "moveBackwardAndModifySelection:") {
276         modifiers |= Qt::ShiftModifier;
277         keycode = Qt::Key_Left;
278     } else if(command =="moveDown:") {
279         keycode = Qt::Key_Down;
280     } else if(command =="moveDownAndModifySelection:") {
281         modifiers |= Qt::ShiftModifier;
282         keycode = Qt::Key_Down;
283     } else if(command =="moveForward:") {
284         keycode = Qt::Key_Right;
285     } else if(command =="moveForwardAndModifySelection:") {
286         modifiers |= Qt::ShiftModifier;
287         keycode = Qt::Key_Right;
288     } else if(command =="moveLeft:") {
289         keycode = Qt::Key_Left;
290     } else if(command =="moveLeftAndModifySelection:") {
291         modifiers |= Qt::ShiftModifier;
292         keycode = Qt::Key_Left;
293     } else if(command =="moveRight:") {
294         keycode = Qt::Key_Right;
295     } else if(command =="moveRightAndModifySelection:") {
296         modifiers |= Qt::ShiftModifier;
297         keycode = Qt::Key_Right;
298     } else if(command =="moveToBeginningOfDocument:") {
299         modifiers |= Qt::ControlModifier;
300         keycode = Qt::Key_Home;
301     } else if(command =="moveToBeginningOfLine:") {
302         keycode = Qt::Key_Home;
303 //     } else if(command =="moveToBeginningOfParagraph:") {
304     } else if(command =="moveToEndOfDocument:") {
305         modifiers |= Qt::ControlModifier;
306         keycode = Qt::Key_End;
307     } else if(command =="moveToEndOfLine:") {
308         keycode = Qt::Key_End;
309 //     } else if(command =="moveToEndOfParagraph:") {
310     } else if(command =="moveUp:") {
311         keycode = Qt::Key_Up;
312     } else if(command =="moveUpAndModifySelection:") {
313         modifiers |= Qt::ShiftModifier;
314         keycode = Qt::Key_Up;
315     } else if(command =="moveWordBackward:") {
316         modifiers |= Qt::ControlModifier;
317         keycode = Qt::Key_Up;
318     } else if(command =="moveWordBackwardAndModifySelection:") {
319         modifiers |= Qt::ShiftModifier;
320         modifiers |= Qt::ControlModifier;
321         keycode = Qt::Key_Left;
322     } else if(command =="moveWordForward:") {
323         modifiers |= Qt::ControlModifier;
324         keycode = Qt::Key_Right;
325     } else if(command =="moveWordForwardAndModifySelection:") {
326         modifiers |= Qt::ControlModifier;
327         modifiers |= Qt::ShiftModifier;
328         keycode = Qt::Key_Right;
329     } else if(command =="moveWordLeft:") {
330         modifiers |= Qt::ControlModifier;
331         keycode = Qt::Key_Left;
332     } else if(command =="moveWordRight:") {
333         modifiers |= Qt::ControlModifier;
334         keycode = Qt::Key_Left;
335     } else if(command =="moveWordRightAndModifySelection:") {
336         modifiers |= Qt::ShiftModifier;
337         modifiers |= Qt::ControlModifier;
338         keycode = Qt::Key_Right;
339     } else if(command =="moveWordLeftAndModifySelection:") {
340         modifiers |= Qt::ShiftModifier;
341         modifiers |= Qt::ControlModifier;
342         keycode = Qt::Key_Left;
343     } else if(command =="pageDown:") {
344         keycode = Qt::Key_PageDown;        
345     } else if(command =="pageUp:") {
346         keycode = Qt::Key_PageUp;        
347     } else if(command == "deleteWordBackward:") {
348         modifiers |= Qt::ControlModifier;
349         keycode = Qt::Key_Backspace;
350     } else if(command == "deleteBackward:") {
351         keycode = Qt::Key_Backspace;
352     } else if(command == "deleteForward:") {
353         keycode = Qt::Key_Delete;
354     }
355     QKeyEvent event(QEvent::KeyPress, keycode, modifiers);
356     QApplication::sendEvent(parent(), &event);
357     QKeyEvent event2(QEvent::KeyRelease, keycode, modifiers);
358     QApplication::sendEvent(parent(), &event2);
359 }