3a98d9dbcb36e2abb3af2200ff6f07ec8a3cbced
[WebKit-https.git] / WebKitTools / DumpRenderTree / DumpRenderTree.qtproj / DumpRenderTree.cpp
1 /*
2  * Copyright (C) 2005, 2006 Apple Computer, Inc.  All rights reserved. 
3  * Copyright (C) 2006 Nikolas Zimmermann <zimmermann@kde.org>
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  *
9  * 1.  Redistributions of source code must retain the above copyright
10  *     notice, this list of conditions and the following disclaimer. 
11  * 2.  Redistributions in binary form must reproduce the above copyright
12  *     notice, this list of conditions and the following disclaimer in the
13  *     documentation and/or other materials provided with the distribution. 
14  * 3.  Neither the name of Apple Computer, Inc. ("Apple") nor the names of
15  *     its contributors may be used to endorse or promote products derived
16  *     from this software without specific prior written permission. 
17  *
18  * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
19  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
20  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
21  * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
22  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
23  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
24  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
25  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
27  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28  */
29
30 #include "config.h"
31 #include "DumpRenderTree.h"
32
33 #include "Page.h"
34 #include "markup.h"
35 #include "Document.h"
36 #include "FrameView.h"
37 #include "KURL.h"
38 #include "FrameLoader.h"
39 #include "RenderTreeAsText.h"
40 #include "ChromeClientQt.h"
41
42 #include <QDir>
43 #include <QFile>
44 #include <QTimer>
45 #include <QBoxLayout>
46 #include <QScrollArea>
47 #include <QApplication>
48
49 #include <unistd.h>
50
51 namespace WebCore {
52
53 // Choose some default values.
54 const unsigned int maxViewWidth = 800;
55 const unsigned int maxViewHeight = 600;
56
57 DumpRenderTree::DumpRenderTree()
58     : m_frame(0)
59     , m_client(new DumpRenderTreeClient())
60     , m_stdin(0)
61     , m_notifier()
62 {
63     // Initialize WebCore in Qt platform mode...
64     Page* page = new Page(new ChromeClientQt());
65     m_frame = new FrameQt(page, 0, m_client);
66
67     page->setMainFrame(m_frame);
68
69     FrameView* view = new FrameView(m_frame);
70     view->setScrollbarsMode(ScrollbarAlwaysOff);
71
72     m_frame->setView(view);
73     view->setParentWidget(0 /* no toplevel widget */);
74
75     // Reverse calculations in QAbstractScrollArea::maximumViewportSize()
76     QScrollArea* area = qobject_cast<QScrollArea*>(m_frame->view()->qwidget());
77
78     unsigned int viewWidth = maxViewWidth + 2 * area->frameWidth();
79     unsigned int viewHeight = maxViewHeight + 2 * area->frameWidth();
80
81     area->resize(viewWidth, viewHeight);
82
83     // Read file containing to be skipped tests...
84     readSkipFile();
85 }
86
87 DumpRenderTree::~DumpRenderTree()
88 {
89     delete m_frame;
90     delete m_client;
91
92     delete m_stdin;
93     delete m_notifier;
94 }
95
96 void DumpRenderTree::open()
97 {
98     if (!m_stdin)
99         m_stdin = new QTextStream(stdin, IO_ReadOnly);
100     
101     if (!m_notifier) {
102         m_notifier = new QSocketNotifier(STDIN_FILENO, QSocketNotifier::Read);
103         connect(m_notifier, SIGNAL(activated(int)), this, SLOT(readStdin(int)));
104     }
105 }
106
107 void DumpRenderTree::open(const KURL& url)
108 {
109     Q_ASSERT(url.isLocalFile());
110
111     // Ignore skipped tests
112     if (m_skipped.indexOf(url.path()) != -1) { 
113         fprintf(stdout, "#EOF\n");
114         fflush(stdout);
115         return;
116     }
117
118     m_frame->client()->openURL(url);
119
120     // Simple poll mechanism, to find out when the page is loaded...
121     checkLoaded();
122 }
123
124 void DumpRenderTree::readStdin(int /* socket */)
125 {
126     // Read incoming data from stdin...
127     QString line = m_stdin->readLine(); 
128     if (!line.isEmpty()) 
129         open(KURL(line.toLatin1()));
130 }
131
132 void DumpRenderTree::readSkipFile()
133 {
134     Q_ASSERT(m_skipped.isEmpty());
135
136     QFile file("WebKitTools/DumpRenderTree/DumpRenderTree.qtproj/tests-skipped.txt");
137     if (!file.exists()) {
138         qFatal("Run DumpRenderTree from the source root directory!\n");
139         return;
140     }
141
142     if (!file.open(QIODevice::ReadOnly | QIODevice::Text)) {
143         qFatal("Couldn't read skip file!\n");
144         return;
145     }
146
147     QString testsPath = QDir::currentPath() + "/LayoutTests/";
148     while (!file.atEnd()) {
149         QByteArray line = file.readLine();
150
151         // Remove trailing line feed
152         line.chop(1);
153
154         // Ignore comments
155         if (line.isEmpty() || line.startsWith('#'))
156             continue;
157
158         m_skipped.append(testsPath + line);
159     }
160 }
161
162 void DumpRenderTree::checkLoaded()
163 {
164     if (m_frame->loader()->isComplete()) {
165         if (!m_notifier) {
166             // Dump markup in single file mode...
167             DeprecatedString markup = createMarkup(m_frame->document());
168             fprintf(stdout, "Source:\n\n%s\n", markup.ascii());
169         }
170
171         // Dump render text...
172         DeprecatedString renderDump = externalRepresentation(m_frame->renderer());
173         fprintf(stdout, "%s#EOF\n", renderDump.ascii());
174         fflush(stdout);
175
176         if (!m_notifier) {
177             // Exit now in single file mode...
178             QApplication::exit();
179         }
180     } else
181         QTimer::singleShot(10, this, SLOT(checkLoaded()));
182 }
183
184 FrameQt* DumpRenderTree::frame() const
185 {
186     return m_frame;
187 }
188
189 }
190
191 #include "DumpRenderTree.moc"