Upstream version 5.34.92.0
[platform/framework/web/crosswalk.git] / src / third_party / WebKit / Source / core / rendering / RenderPart.cpp
1 /*
2  * Copyright (C) 1999 Lars Knoll (knoll@kde.org)
3  *           (C) 2000 Simon Hausmann <hausmann@kde.org>
4  *           (C) 2000 Stefan Schimanski (1Stein@gmx.de)
5  * Copyright (C) 2004, 2005, 2006, 2009 Apple Inc. All rights reserved.
6  * Copyright (C) Research In Motion Limited 2011. All rights reserved.
7  *
8  * This library is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Library General Public
10  * License as published by the Free Software Foundation; either
11  * version 2 of the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16  * Library General Public License for more details.
17  *
18  * You should have received a copy of the GNU Library General Public License
19  * along with this library; see the file COPYING.LIB.  If not, write to
20  * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
21  * Boston, MA 02110-1301, USA.
22  *
23  */
24
25 #include "config.h"
26 #include "core/rendering/RenderPart.h"
27
28 #include "core/frame/Frame.h"
29 #include "core/frame/FrameView.h"
30 #include "core/html/HTMLFrameElementBase.h"
31 #include "core/plugins/PluginView.h"
32 #include "core/rendering/HitTestResult.h"
33 #include "core/rendering/RenderLayer.h"
34 #include "core/rendering/RenderView.h"
35 #include "core/rendering/svg/RenderSVGRoot.h"
36
37 using namespace std;
38
39 namespace WebCore {
40
41 RenderPart::RenderPart(Element* node)
42     : RenderWidget(node)
43 {
44     setInline(false);
45 }
46
47 RenderPart::~RenderPart()
48 {
49     clearWidget();
50 }
51
52 void RenderPart::setWidget(PassRefPtr<Widget> widget)
53 {
54     if (widget == this->widget())
55         return;
56
57     RenderWidget::setWidget(widget);
58 }
59
60 LayerType RenderPart::layerTypeRequired() const
61 {
62     LayerType type = RenderWidget::layerTypeRequired();
63     if (type != NoLayer)
64         return type;
65
66     return requiresAcceleratedCompositing() ? NormalLayer : NoLayer;
67 }
68
69 bool RenderPart::requiresAcceleratedCompositing() const
70 {
71     // There are two general cases in which we can return true. First, if this is a plugin
72     // renderer and the plugin has a layer, then we need a layer. Second, if this is
73     // a renderer with a contentDocument and that document needs a layer, then we need
74     // a layer.
75     if (widget() && widget()->isPluginView() && toPluginView(widget())->platformLayer())
76         return true;
77
78     if (!node() || !node()->isFrameOwnerElement())
79         return false;
80
81     HTMLFrameOwnerElement* element = toHTMLFrameOwnerElement(node());
82     if (element->contentFrame() && element->contentFrame()->remotePlatformLayer())
83         return true;
84
85     if (Document* contentDocument = element->contentDocument()) {
86         if (RenderView* view = contentDocument->renderView())
87             return view->usesCompositing();
88     }
89
90     return false;
91 }
92
93 bool RenderPart::needsPreferredWidthsRecalculation() const
94 {
95     if (RenderWidget::needsPreferredWidthsRecalculation())
96         return true;
97     return embeddedContentBox();
98 }
99
100 RenderBox* RenderPart::embeddedContentBox() const
101 {
102     if (!node() || !widget() || !widget()->isFrameView())
103         return 0;
104     return toFrameView(widget())->embeddedContentBox();
105 }
106
107 bool RenderPart::nodeAtPoint(const HitTestRequest& request, HitTestResult& result, const HitTestLocation& locationInContainer, const LayoutPoint& accumulatedOffset, HitTestAction action)
108 {
109     if (!widget() || !widget()->isFrameView() || !request.allowsChildFrameContent())
110         return RenderWidget::nodeAtPoint(request, result, locationInContainer, accumulatedOffset, action);
111
112     FrameView* childFrameView = toFrameView(widget());
113     RenderView* childRoot = childFrameView->renderView();
114
115     if (childRoot) {
116         LayoutPoint adjustedLocation = accumulatedOffset + location();
117         LayoutPoint contentOffset = LayoutPoint(borderLeft() + paddingLeft(), borderTop() + paddingTop()) - childFrameView->scrollOffset();
118         HitTestLocation newHitTestLocation(locationInContainer, -adjustedLocation - contentOffset);
119         HitTestRequest newHitTestRequest(request.type() | HitTestRequest::ChildFrameHitTest);
120         HitTestResult childFrameResult(newHitTestLocation);
121
122         bool isInsideChildFrame = childRoot->hitTest(newHitTestRequest, newHitTestLocation, childFrameResult);
123
124         if (newHitTestLocation.isRectBasedTest())
125             result.append(childFrameResult);
126         else if (isInsideChildFrame)
127             result = childFrameResult;
128
129         if (isInsideChildFrame)
130             return true;
131
132         if (request.allowsFrameScrollbars()) {
133             // ScrollView scrollbars are not the same as RenderLayer scrollbars tested by RenderLayer::hitTestOverflowControls,
134             // so we need to test ScrollView scrollbars separately here.
135             // FIXME: Consider if this test could be done unconditionally.
136             Scrollbar* frameScrollbar = childFrameView->scrollbarAtPoint(newHitTestLocation.roundedPoint());
137             if (frameScrollbar)
138                 result.setScrollbar(frameScrollbar);
139         }
140     }
141
142     return RenderWidget::nodeAtPoint(request, result, locationInContainer, accumulatedOffset, action);
143 }
144
145 }