bool RenderIFrame::flattenFrame() const { if (!node() || !node()->hasTagName(iframeTag)) return false; HTMLIFrameElement* element = static_cast<HTMLIFrameElement*>(node()); Frame* frame = element->document()->frame(); if (isSeamless()) return false; // Seamless iframes are already "flat", don't try to flatten them. bool enabled = frame && frame->settings() && frame->settings()->frameFlatteningEnabled(); if (!enabled || !frame->page()) return false; if (style()->width().isFixed() && style()->height().isFixed()) { // Do not flatten iframes with scrolling="no". if (element->scrollingMode() == ScrollbarAlwaysOff) return false; if (style()->width().value() <= 0 || style()->height().value() <= 0) return false; } // Do not flatten offscreen inner frames during frame flattening, as flattening might make them visible. IntRect boundingRect = absoluteBoundingBoxRectIgnoringTransforms(); return boundingRect.maxX() > 0 && boundingRect.maxY() > 0; }
bool RenderIFrame::flattenFrame() { if (!node() || !node()->hasTagName(iframeTag)) return false; // CAPPFIX_WEB_HTML5: SECURITY if (isSeamless()) return false; // Seamless iframes are already "flat", don't try to flatten them. // CAPPFIX_WEB_HTML5_END HTMLIFrameElement* element = static_cast<HTMLIFrameElement*>(node()); bool isScrollable = element->scrollingMode() != ScrollbarAlwaysOff; if (!isScrollable && style()->width().isFixed() && style()->height().isFixed()) return false; Frame* frame = element->document()->frame(); bool enabled = frame && frame->settings()->frameFlatteningEnabled(); if (!enabled || !frame->page()) return false; FrameView* view = frame->page()->mainFrame()->view(); if (!view) return false; // Do not flatten offscreen inner frames during frame flattening. return absoluteBoundingBoxRect().intersects(IntRect(IntPoint(0, 0), view->contentsSize())); }
TEST_F(FrameThrottlingTest, HiddenSameOriginFramesAreNotThrottled) { SimRequest mainResource("https://example.com/", "text/html"); SimRequest frameResource("https://example.com/iframe.html", "text/html"); loadURL("https://example.com/"); mainResource.complete("<iframe id=frame src=iframe.html></iframe>"); frameResource.complete("<iframe id=innerFrame></iframe>"); auto* frameElement = toHTMLIFrameElement(document().getElementById("frame")); auto* frameDocument = frameElement->contentDocument(); HTMLIFrameElement* innerFrameElement = toHTMLIFrameElement(frameDocument->getElementById("innerFrame")); auto* innerFrameDocument = innerFrameElement->contentDocument(); EXPECT_FALSE(document().view()->canThrottleRendering()); EXPECT_FALSE(frameDocument->view()->canThrottleRendering()); EXPECT_FALSE(innerFrameDocument->view()->canThrottleRendering()); // Hidden same origin frames are not throttled. frameElement->setAttribute(styleAttr, "transform: translateY(480px)"); compositeFrame(); EXPECT_FALSE(document().view()->canThrottleRendering()); EXPECT_FALSE(frameDocument->view()->canThrottleRendering()); EXPECT_FALSE(innerFrameDocument->view()->canThrottleRendering()); }
static v8::Handle<v8::Value> contentDocumentAttrGetter(v8::Local<v8::String> name, const v8::AccessorInfo& info) { INC_STATS("DOM.HTMLIFrameElement.contentDocument._get"); HTMLIFrameElement* imp = V8HTMLIFrameElement::toNative(info.Holder()); if (!V8BindingSecurity::checkNodeSecurity(V8BindingState::Only(), imp->contentDocument())) return v8::Handle<v8::Value>(); return toV8(imp->contentDocument()); }
static void collectActiveCSSStyleSheetsFromSeamlessParents(Vector<RefPtr<CSSStyleSheet> >& sheets, Document* document) { HTMLIFrameElement* seamlessParentIFrame = document->seamlessParentIFrame(); if (!seamlessParentIFrame) return; sheets.appendVector(seamlessParentIFrame->document()->styleSheetCollection()->activeAuthorStyleSheets()); }
bool RenderIFrame::flattenFrame() { if (!node() || !node()->hasTagName(iframeTag)) return false; HTMLIFrameElement* element = static_cast<HTMLIFrameElement*>(node()); bool isScrollable = element->scrollingMode() != ScrollbarAlwaysOff; if (style()->width().isFixed() && style()->height().isFixed()) { if (!isScrollable) return false; if (style()->width().value() <= 0 || style()->height().value() <= 0) return false; } Frame* frame = element->document()->frame(); bool enabled = frame && frame->settings()->frameFlatteningEnabled(); if (!enabled || !frame->page()) return false; FrameView* view = frame->page()->mainFrame()->view(); if (!view) return false; // Do not flatten offscreen inner frames during frame flattening, as flattening might make them visible. IntRect boundingRect = absoluteBoundingBoxRect(); return boundingRect.maxX() > 0 && boundingRect.maxY() > 0; }
bool RenderIFrame::flattenFrame() { if (!node() || !node()->hasTagName(iframeTag)) return false; HTMLIFrameElement* element = static_cast<HTMLIFrameElement*>(node()); bool isScrollable = element->scrollingMode() != ScrollbarAlwaysOff; if (style()->width().isFixed() && style()->height().isFixed()) { if (!isScrollable) return false; if (style()->width().value() <= 0 || style()->height().value() <= 0) return false; } Frame* frame = element->document()->frame(); bool enabled = frame && frame->settings()->frameFlatteningEnabled(); if (!enabled || !frame->page()) return false; FrameView* view = frame->page()->mainFrame()->view(); if (!view) return false; // Do not flatten offscreen inner frames during frame flattening. return absoluteBoundingBoxRect().intersects(IntRect(IntPoint(0, 0), view->contentsSize())); }
JSValue jsHTMLIFrameElementWidth(ExecState* exec, JSValue slotBase, const Identifier&) { JSHTMLIFrameElement* castedThis = static_cast<JSHTMLIFrameElement*>(asObject(slotBase)); UNUSED_PARAM(exec); HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(castedThis->impl()); JSValue result = jsString(exec, imp->getAttribute(HTMLNames::widthAttr)); return result; }
JSValue jsHTMLIFrameElementContentWindow(ExecState* exec, JSValue slotBase, const Identifier&) { JSHTMLIFrameElement* castedThis = static_cast<JSHTMLIFrameElement*>(asObject(slotBase)); UNUSED_PARAM(exec); HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(castedThis->impl()); JSValue result = toJS(exec, castedThis->globalObject(), WTF::getPtr(imp->contentWindow())); return result; }
HRESULT STDMETHODCALLTYPE DOMHTMLIFrameElement::contentFrame( /* [retval][out] */ IWebFrame **result) { if (!result) return E_POINTER; *result = 0; ASSERT(m_element && m_element->hasTagName(iframeTag)); HTMLIFrameElement* iFrameElement = static_cast<HTMLIFrameElement*>(m_element); COMPtr<IWebFrame> webFrame = kit(iFrameElement->contentFrame()); if (!webFrame) return E_FAIL; return webFrame.copyRefTo(result); }
void JSHTMLIFrameElement::setSrc(ExecState* exec, JSValue* value) { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); String srcValue = valueToStringWithNullCheck(exec, value); if (protocolIs(parseURL(srcValue), "javascript")) { if (!checkNodeSecurity(exec, imp->contentDocument())) return; } imp->setSrc(srcValue); }
void JSHTMLIFrameElement::setSrc(ExecState* exec, JSValue value) { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); String srcValue = valueToStringWithNullCheck(exec, value); if (protocolIsJavaScript(deprecatedParseURL(srcValue))) { Document* contentDocument = imp->contentDocument(); if (contentDocument && !checkNodeSecurity(exec, contentDocument)) return; } imp->setAttribute(srcAttr, srcValue); }
void RenderPartObject::calcWidth() { RenderPart::calcWidth(); if (!flattenFrame()) return; HTMLIFrameElement* frame = static_cast<HTMLIFrameElement*>(node()); bool isScrollable = frame->scrollingMode() != ScrollbarAlwaysOff; if (isScrollable || !style()->width().isFixed()) { FrameView* view = static_cast<FrameView*>(widget()); int border = borderLeft() + borderRight(); setWidth(max(width(), view->contentsWidth() + border)); } }
JSValue JSC_HOST_CALL jsHTMLIFrameElementPrototypeFunctionGetSVGDocument(ExecState* exec, JSObject*, JSValue thisValue, const ArgList& args) { UNUSED_PARAM(args); if (!thisValue.inherits(&JSHTMLIFrameElement::s_info)) return throwError(exec, TypeError); JSHTMLIFrameElement* castedThisObj = static_cast<JSHTMLIFrameElement*>(asObject(thisValue)); HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(castedThisObj->impl()); ExceptionCode ec = 0; if (!checkNodeSecurity(exec, imp->getSVGDocument(ec))) return jsUndefined(); JSC::JSValue result = toJS(exec, castedThisObj->globalObject(), WTF::getPtr(imp->getSVGDocument(ec))); setDOMException(exec, ec); return result; }
EncodedJSValue JSC_HOST_CALL jsHTMLIFrameElementPrototypeFunctionGetSVGDocument(ExecState* exec) { JSValue thisValue = exec->hostThisValue(); if (!thisValue.inherits(&JSHTMLIFrameElement::s_info)) return throwVMTypeError(exec); JSHTMLIFrameElement* castedThis = static_cast<JSHTMLIFrameElement*>(asObject(thisValue)); HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(castedThis->impl()); ExceptionCode ec = 0; if (!checkNodeSecurity(exec, imp->getSVGDocument(ec))) return JSValue::encode(jsUndefined()); JSC::JSValue result = toJS(exec, castedThis->globalObject(), WTF::getPtr(imp->getSVGDocument(ec))); setDOMException(exec, ec); return JSValue::encode(result); }
void RenderIFrame::computeLogicalHeight() { RenderPart::computeLogicalHeight(); if (!flattenFrame()) return; HTMLIFrameElement* frame = static_cast<HTMLIFrameElement*>(node()); bool isScrollable = frame->scrollingMode() != ScrollbarAlwaysOff; if (isScrollable || !style()->height().isFixed()) { FrameView* view = static_cast<FrameView*>(widget()); if (!view) return; int border = borderTop() + borderBottom(); setHeight(max(height(), view->contentsHeight() + border)); } }
void RenderPartObject::viewCleared() { if (element() && m_widget && m_widget->isFrameView()) { FrameView* view = static_cast<FrameView*>(m_widget); int marginw = -1; int marginh = -1; if (element()->hasTagName(iframeTag)) { HTMLIFrameElement* frame = static_cast<HTMLIFrameElement*>(element()); marginw = frame->getMarginWidth(); marginh = frame->getMarginHeight(); } if (marginw != -1) view->setMarginWidth(marginw); if (marginh != -1) view->setMarginHeight(marginh); } }
void RenderEmbeddedObject::viewCleared() { // This is required for <object> elements whose contents are rendered by WebCore (e.g. src="foo.html"). if (node() && widget() && widget()->isFrameView()) { FrameView* view = toFrameView(widget()); int marginWidth = -1; int marginHeight = -1; if (node()->hasTagName(iframeTag)) { HTMLIFrameElement* frame = toHTMLIFrameElement(node()); marginWidth = frame->marginWidth(); marginHeight = frame->marginHeight(); } if (marginWidth != -1) view->setMarginWidth(marginWidth); if (marginHeight != -1) view->setMarginHeight(marginHeight); } }
void RenderIFrame::computeLogicalWidth() { // CAPPFIX_WEB_HTML5: SECURITY // When we're seamless, we behave like a block. Thankfully RenderBox has all the right logic for this. if (isSeamless()) return RenderBox::computeLogicalWidth(); // CAPPFIX_WEB_HTML5_END RenderPart::computeLogicalWidth(); if (!flattenFrame()) return; HTMLIFrameElement* frame = static_cast<HTMLIFrameElement*>(node()); bool isScrollable = frame->scrollingMode() != ScrollbarAlwaysOff; if (isScrollable || !style()->width().isFixed()) { FrameView* view = static_cast<FrameView*>(widget()); if (!view) return; int border = borderLeft() + borderRight(); setWidth(max(width(), view->contentsWidth() + border)); } }
// static bool HTMLIFrameElementPayments::fastHasAttribute( const QualifiedName& name, const HTMLIFrameElement& element) { DCHECK(name == HTMLNames::allowpaymentrequestAttr); return element.fastHasAttribute(name); }
// static void HTMLIFrameElementPayments::setBooleanAttribute(const QualifiedName& name, HTMLIFrameElement& element, bool value) { DCHECK(name == HTMLNames::allowpaymentrequestAttr); element.setBooleanAttribute(name, value); }
// static bool HTMLIFrameElementPayments::allowPaymentRequest( HTMLIFrameElement& element) { return element.fastHasAttribute(HTMLNames::allowpaymentrequestAttr); }
void setJSHTMLIFrameElementSrc(ExecState* exec, JSObject* thisObject, JSValue value) { JSHTMLIFrameElement* castedThis = static_cast<JSHTMLIFrameElement*>(thisObject); HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(castedThis->impl()); imp->setAttribute(WebCore::HTMLNames::srcAttr, valueToStringWithNullCheck(exec, value)); }
JSValue* JSHTMLIFrameElement::getValueProperty(ExecState* exec, int token) const { switch (token) { case AlignAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); return jsString(exec, imp->align()); } case FrameBorderAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); return jsString(exec, imp->frameBorder()); } case HeightAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); return jsString(exec, imp->height()); } case LongDescAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); return jsString(exec, imp->longDesc()); } case MarginHeightAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); return jsString(exec, imp->marginHeight()); } case MarginWidthAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); return jsString(exec, imp->marginWidth()); } case NameAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); return jsString(exec, imp->name()); } case ScrollingAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); return jsString(exec, imp->scrolling()); } case SrcAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); return jsString(exec, imp->src()); } case WidthAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); return jsString(exec, imp->width()); } case ContentDocumentAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); return checkNodeSecurity(exec, imp->contentDocument()) ? toJS(exec, WTF::getPtr(imp->contentDocument())) : jsUndefined(); } case ContentWindowAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); return toJS(exec, WTF::getPtr(imp->contentWindow())); } case ConstructorAttrNum: return getConstructor(exec); } return 0; }
JSValue jsHTMLIFrameElementContentDocument(ExecState* exec, JSValue slotBase, const Identifier&) { JSHTMLIFrameElement* castedThis = static_cast<JSHTMLIFrameElement*>(asObject(slotBase)); HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(castedThis->impl()); return checkNodeSecurity(exec, imp->contentDocument()) ? toJS(exec, castedThis->globalObject(), WTF::getPtr(imp->contentDocument())) : jsUndefined(); }
void JSHTMLIFrameElement::putValueProperty(ExecState* exec, int token, JSValue* value) { switch (token) { case AlignAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); imp->setAlign(valueToStringWithNullCheck(exec, value)); break; } case FrameBorderAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); imp->setFrameBorder(valueToStringWithNullCheck(exec, value)); break; } case HeightAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); imp->setHeight(valueToStringWithNullCheck(exec, value)); break; } case LongDescAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); imp->setLongDesc(valueToStringWithNullCheck(exec, value)); break; } case MarginHeightAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); imp->setMarginHeight(valueToStringWithNullCheck(exec, value)); break; } case MarginWidthAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); imp->setMarginWidth(valueToStringWithNullCheck(exec, value)); break; } case NameAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); imp->setName(valueToStringWithNullCheck(exec, value)); break; } case ScrollingAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); imp->setScrolling(valueToStringWithNullCheck(exec, value)); break; } case SrcAttrNum: { setSrc(exec, value); break; } case WidthAttrNum: { HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(impl()); imp->setWidth(valueToStringWithNullCheck(exec, value)); break; } } }
void RenderPartObject::layout() { ASSERT(needsLayout()); #ifdef FLATTEN_IFRAME RenderPart::calcWidth(); RenderPart::calcHeight(); // Calculate the styled dimensions by subtracting the border and padding. int extraWidth = paddingLeft() + paddingRight() + borderLeft() + borderRight(); int extraHeight = paddingTop() + paddingBottom() + borderTop() + borderBottom(); int styleWidth = width() - extraWidth; int styleHeight = height() - extraHeight; // Some IFrames have a width and/or height of 1 when they are meant to be // hidden. If that is the case, do not try to expand. if (node()->hasTagName(iframeTag) && widget() && widget()->isFrameView() && styleWidth > 1 && styleHeight > 1) { HTMLIFrameElement* element = static_cast<HTMLIFrameElement*>(node()); bool scrolling = element->scrollingMode() != ScrollbarAlwaysOff; bool widthIsFixed = style()->width().isFixed(); bool heightIsFixed = style()->height().isFixed(); // If an iframe has a fixed dimension and suppresses scrollbars, it // will disrupt layout if we force it to expand. Plus on a desktop, // the extra content is not accessible. if (scrolling || !widthIsFixed || !heightIsFixed) { FrameView* view = static_cast<FrameView*>(widget()); RenderView* root = view ? view->frame()->contentRenderer() : NULL; if (root && style()->visibility() != HIDDEN) { // Update the dimensions to get the correct minimum preferred // width updateWidgetPosition(); // Use the preferred width if it is larger and only if // scrollbars are visible or the width style is not fixed. if (scrolling || !widthIsFixed) setWidth(max(width(), root->minPrefWidth()) + extraWidth); // Resize the view to recalc the height. int h = height() - extraHeight; int w = width() - extraWidth; if (w > view->width()) h = 0; if (w != view->width() || h != view->height()) { view->resize(w, h); } // Layout the view. //SAMSUNG CHANGE >> // Browser freeze issue in http://www.enuri.com/ /* do { view->layout(); } while (view->layoutPending() || root->needsLayout()); */ node()->document()->page()->mainFrame()->view()->layoutIfNeededRecursive(); //SAMSUNG CHANGE << int contentHeight = view->contentsHeight(); int contentWidth = view->contentsWidth(); // Only change the width or height if scrollbars are visible or // if the style is not a fixed value. Use the maximum value so // that iframes never shrink. if (scrolling || !heightIsFixed) setHeight(max(height(), contentHeight + extraHeight)); if (scrolling || !widthIsFixed) setWidth(max(width(), contentWidth + extraWidth)); // Update one last time updateWidgetPosition(); // Layout one more time to ensure all objects have the correct // height. view->layout(); #if !ASSERT_DISABLED ASSERT(!view->layoutPending()); ASSERT(!root->needsLayout()); // Sanity check when assertions are enabled. RenderObject* c = root->nextInPreOrder(); while (c) { ASSERT(!c->needsLayout()); c = c->nextInPreOrder(); } #endif } } } #else calcWidth(); calcHeight(); #endif RenderPart::layout(); m_overflow.clear(); addShadowOverflow(); setNeedsLayout(false); }
static v8::Handle<v8::Value> contentWindowAttrGetter(v8::Local<v8::String> name, const v8::AccessorInfo& info) { INC_STATS("DOM.HTMLIFrameElement.contentWindow._get"); HTMLIFrameElement* imp = V8HTMLIFrameElement::toNative(info.Holder()); return toV8(imp->contentWindow()); }
void setJSHTMLIFrameElementWidth(ExecState* exec, JSObject* thisObject, JSValue value) { JSHTMLIFrameElement* castedThisObj = static_cast<JSHTMLIFrameElement*>(thisObject); HTMLIFrameElement* imp = static_cast<HTMLIFrameElement*>(castedThisObj->impl()); imp->setAttribute(HTMLNames::widthAttr, valueToStringWithNullCheck(exec, value)); }