Bug 1365660: Part 2 - Add a HasRemoteContent flag to popup widgets that contain remote browsers. r=kats,bas

There are several behaviors that we only need to apply to popups which are
known to contain remote content. And since those behaviors can cause issues
elsewhere, we need to be able to identify popups which should contain remote
content, and treat them specially, where appropriate.

MozReview-Commit-ID: EMFrSP8lZiD

--HG--
extra : rebase_source : 5ee9da422081098d8099a048c7704008a06a7241
This commit is contained in:
Kris Maglione 2017-05-17 10:16:25 -07:00
Родитель 6f66a39352
Коммит 444c7656ff
6 изменённых файлов: 37 добавлений и 3 удалений

Просмотреть файл

@ -1103,6 +1103,7 @@ GK_ATOM(refresh, "refresh")
GK_ATOM(rel, "rel")
GK_ATOM(onreloadpage, "onreloadpage")
GK_ATOM(rem, "rem")
GK_ATOM(remote, "remote")
GK_ATOM(removeelement, "removeelement")
GK_ATOM(renderingobserverlist, "renderingobserverlist")
GK_ATOM(repeat, "repeat")

Просмотреть файл

@ -189,6 +189,14 @@ nsMenuPopupFrame::Init(nsIContent* aContent,
AddStateBits(NS_FRAME_IN_POPUP);
}
bool
nsMenuPopupFrame::HasRemoteContent() const
{
return (!mInContentShell && mPopupType == ePopupTypePanel &&
mContent->AttrValueIs(kNameSpaceID_None, nsGkAtoms::remote,
nsGkAtoms::_true, eIgnoreCase));
}
bool
nsMenuPopupFrame::IsNoAutoHide() const
{
@ -240,9 +248,12 @@ nsMenuPopupFrame::PopupLevel(bool aIsNoAutoHide) const
}
void
nsMenuPopupFrame::EnsureWidget()
nsMenuPopupFrame::EnsureWidget(bool aRecreate)
{
nsView* ourView = GetView();
if (aRecreate) {
ourView->DestroyWidget();
}
if (!ourView->HasWidget()) {
NS_ASSERTION(!mGeneratedChildren && !PrincipalChildList().FirstChild(),
"Creating widget for MenuPopupFrame with children");
@ -291,11 +302,14 @@ nsMenuPopupFrame::CreateWidgetForView(nsView* aView)
}
}
bool remote = HasRemoteContent();
nsTransparencyMode mode = nsLayoutUtils::GetFrameTransparency(this, this);
nsIContent* parentContent = GetContent()->GetParent();
nsIAtom *tag = nullptr;
if (parentContent && parentContent->IsXULElement())
tag = parentContent->NodeInfo()->NameAtom();
widgetData.mHasRemoteContent = remote;
widgetData.mSupportTranslucency = mode == eTransparencyTransparent;
widgetData.mDropShadow = !(mode == eTransparencyTransparent || tag == nsGkAtoms::menulist);
widgetData.mPopupLevel = PopupLevel(widgetData.mNoAutoHide);
@ -2234,6 +2248,13 @@ nsMenuPopupFrame::AttributeChanged(int32_t aNameSpaceID,
}
#endif
if (aAttribute == nsGkAtoms::remote) {
// When the remote attribute changes, we need to create a new widget to
// ensure that it has the correct compositor and transparency settings to
// match the new value.
EnsureWidget(true);
}
if (aAttribute == nsGkAtoms::followanchor) {
nsXULPopupManager* pm = nsXULPopupManager::GetInstance();
if (pm) {

Просмотреть файл

@ -225,6 +225,8 @@ public:
virtual void DestroyFrom(nsIFrame* aDestructRoot) override;
bool HasRemoteContent() const;
// returns true if the popup is a panel with the noautohide attribute set to
// true. These panels do not roll up automatically.
bool IsNoAutoHide() const;
@ -234,7 +236,10 @@ public:
return PopupLevel(IsNoAutoHide());
}
void EnsureWidget();
// Ensure that a widget has already been created for this view, and create
// one if it hasn't. If aRecreate is true, destroys any existing widget and
// creates a new one, regardless of whether one has already been created.
void EnsureWidget(bool aRecreate = false);
nsresult CreateWidgetForView(nsView* aView);
uint8_t GetShadowStyle();

Просмотреть файл

@ -163,6 +163,7 @@ nsBaseWidget::nsBaseWidget()
, mSizeMode(nsSizeMode_Normal)
, mPopupLevel(ePopupLevelTop)
, mPopupType(ePopupTypeAny)
, mHasRemoteContent(false)
, mCompositorWidgetDelegate(nullptr)
, mUpdateCursor(true)
, mUseAttachedEvents(false)
@ -380,6 +381,7 @@ void nsBaseWidget::BaseCreate(nsIWidget* aParent,
mBorderStyle = aInitData->mBorderStyle;
mPopupLevel = aInitData->mPopupLevel;
mPopupType = aInitData->mPopupHint;
mHasRemoteContent = aInitData->mHasRemoteContent;
}
if (aParent) {

Просмотреть файл

@ -549,6 +549,8 @@ protected:
nsPopupType PopupType() const { return mPopupType; }
bool HasRemoteContent() const { return mHasRemoteContent; }
void NotifyRollupGeometryChange()
{
// XULPopupManager isn't interested in this notification, so only
@ -683,6 +685,7 @@ protected:
nsPopupLevel mPopupLevel;
nsPopupType mPopupType;
SizeConstraints mSizeConstraints;
bool mHasRemoteContent;
CompositorWidgetDelegate* mCompositorWidgetDelegate;

Просмотреть файл

@ -105,7 +105,8 @@ struct nsWidgetInitData {
mIsDragPopup(false),
mIsAnimationSuppressed(false),
mSupportTranslucency(false),
mMouseTransparent(false)
mMouseTransparent(false),
mHasRemoteContent(false)
{
}
@ -131,6 +132,7 @@ struct nsWidgetInitData {
// true if the window should be transparent to mouse events. Currently this is
// only valid for eWindowType_popup widgets
bool mMouseTransparent;
bool mHasRemoteContent;
};
#endif // nsWidgetInitData_h__