fix a crash on exit
[WebKit-https.git] / WebKitQt / Api / qwebframe.cpp
1 /*
2     Copyright (C) 2007 Trolltech ASA
3     Copyright (C) 2007 Staikos Computing Services Inc.
4
5     This library is free software; you can redistribute it and/or
6     modify it under the terms of the GNU Library General Public
7     License as published by the Free Software Foundation; either
8     version 2 of the License, or (at your option) any later version.
9
10     This library is distributed in the hope that it will be useful,
11     but WITHOUT ANY WARRANTY; without even the implied warranty of
12     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13     Library General Public License for more details.
14
15     You should have received a copy of the GNU Library General Public License
16     along with this library; see the file COPYING.LIB.  If not, write to
17     the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18     Boston, MA 02111-1307, USA.
19
20     This class provides all functionality needed for loading images, style sheets and html
21     pages from the web. It has a memory cache for these objects.
22 */
23 #include "qwebframe.h"
24 #include "qwebpage.h"
25 #include "qwebpage_p.h"
26 #include "qwebframe_p.h"
27
28 #include <qdebug.h>
29
30 #include "FrameLoaderClientQt.h"
31 #include "FrameQt.h"
32 #include "FrameTree.h"
33 #include "FrameView.h"
34 #include "ResourceRequest.h"
35
36 #include "markup.h"
37 #include "RenderTreeAsText.h"
38 #include "Element.h"
39 #include "Document.h"
40 #include "RenderObject.h"
41
42 #include "bindings/runtime.h"
43 #include "bindings/runtime_root.h"
44 #include "ExecState.h"
45 #include "object.h"
46
47 #include "wtf/HashMap.h"
48
49 using namespace WebCore;
50
51 QWebFrame::QWebFrame(QWebPage *parent, QWebFrameData *frameData)
52     : QScrollArea(parent)
53     , d(new QWebFramePrivate)
54 {
55     d->page = parent;
56
57     d->frameLoaderClient = new FrameLoaderClientQt();
58     d->frame = new FrameQt(parent->d->page, frameData->ownerElement, d->frameLoaderClient);
59     d->frameLoaderClient->setFrame(this, d->frame.get());
60
61     d->frameView = new FrameView(d->frame.get());
62     d->frameView->deref();
63     d->frameView->setScrollArea(this);
64     d->frameView->setAllowsScrolling(frameData->allowsScrolling);
65     d->frame->setView(d->frameView.get());
66     if (!frameData->url.isEmpty()) {
67         ResourceRequest request(frameData->url, frameData->referrer);
68         d->frame->loader()->load(request, frameData->name);
69     }
70 }
71
72
73 QWebFrame::QWebFrame(QWebFrame *parent, QWebFrameData *frameData)
74     : QScrollArea(parent->widget())
75     , d(new QWebFramePrivate)
76 {
77     setLineWidth(0);
78     setMidLineWidth(0);
79     setFrameShape(QFrame::NoFrame);
80     d->page = parent->d->page;
81
82     d->frameLoaderClient = new FrameLoaderClientQt();
83     d->frame = new FrameQt(parent->d->page->d->page, frameData->ownerElement, d->frameLoaderClient);
84     d->frameLoaderClient->setFrame(this, d->frame.get());
85
86     d->frameView = new FrameView(d->frame.get());
87     d->frameView->deref();
88     d->frameView->setScrollArea(this);
89     d->frameView->setAllowsScrolling(frameData->allowsScrolling);
90     d->frame->setView(d->frameView.get());
91 }
92
93 QWebFrame::~QWebFrame()
94 {
95     Q_ASSERT(d->frame == 0);
96     Q_ASSERT(d->frameView == 0);
97     delete d;
98 }
99
100 void QWebFrame::addToJSWindowObject(const QByteArray &name, QObject *object)
101 {
102     KJS::Bindings::RootObject *root = d->frame->bindingRootObject();
103     KJS::ExecState *exec = root->interpreter()->globalExec();
104     KJS::JSObject *rootObject = root->interpreter()->globalObject();
105     KJS::JSObject *window = rootObject->get(exec, KJS::Identifier("window"))->getObject();
106     if (!window) {
107         qDebug() << "Warning: couldn't get window object";
108         return;
109     }
110             
111     KJS::JSObject *testController =
112         KJS::Bindings::Instance::createRuntimeObject(KJS::Bindings::Instance::QtLanguage,
113                                                      object, root);
114
115     window->put(exec, KJS::Identifier(name.constData()), testController);
116 }
117
118
119 QString QWebFrame::markup() const
120 {
121     return createMarkup(d->frame->document());
122 }
123
124 QString QWebFrame::innerText() const
125 {
126     if (d->frameView->layoutPending())
127         d->frameView->layout();
128     
129     Element *documentElement = d->frame->document()->documentElement();
130     return documentElement->innerText();
131 }
132
133 QString QWebFrame::renderTreeDump() const
134 {
135     if (d->frameView->layoutPending())
136         d->frameView->layout();
137     
138     return externalRepresentation(d->frame->renderer());
139 }
140
141 QString QWebFrame::title() const
142 {
143     if (d->frame->document())
144         return d->frame->document()->title();
145     else return QString();
146 }
147
148 QWebPage * QWebFrame::page() const
149 {
150     return d->page;
151 }
152
153 QString QWebFrame::selectedText() const
154 {
155     return d->frame->selectedText();
156 }
157
158 void QWebFrame::resizeEvent(QResizeEvent *e)
159 {
160     QScrollArea::resizeEvent(e);
161     if (d->frame && d->frameView) {
162         RenderObject *renderer = d->frame->renderer();
163         if (renderer)
164             renderer->setNeedsLayout(true);
165         d->frameView->scheduleRelayout();
166     }
167 }
168
169 QList<QWebFrame*> QWebFrame::childFrames() const
170 {
171     QList<QWebFrame*> rc;
172     if (d->frame) {
173         FrameTree *tree = d->frame->tree();
174         for (Frame *child = tree->firstChild(); child; child = child->tree()->nextSibling()) {
175             FrameLoaderClientQt *loader = (FrameLoaderClientQt*)child->loader();
176             rc.append(loader->webFrame());
177         }
178
179     }
180     return rc;
181 }
182
183 #include "qwebframe.moc"