Bug 1937785 - Remove nsPresContext::mKeyboardHeight and introduce MobileViewportManager::mPendingKeyboardHeight. r=botond

There's a race condition where the keyboard height change notification
has arrived but nsDocumentViewer size change hasn't yet arrived.

MobileViewportManager::mPendingKeyboardHeight is introduced to fix the race.

Differential Revision: https://phabricator.services.mozilla.com/D234262
This commit is contained in:
Hiroyuki Ikezoe
2025-01-21 06:49:56 +00:00
parent c1967e39f8
commit 5b51ae9cf1
5 changed files with 24 additions and 12 deletions

View File

@@ -648,6 +648,12 @@ void MobileViewportManager::RefreshViewportSize(bool aForceAdjustResolution) {
return; return;
} }
// Now it's time to update the keyboard height
if (mPendingKeyboardHeight) {
mKeyboardHeight = *mPendingKeyboardHeight;
mPendingKeyboardHeight.reset();
}
nsViewportInfo viewportInfo = nsViewportInfo viewportInfo =
mContext->GetViewportInfo(GetLayoutDisplaySize()); mContext->GetViewportInfo(GetLayoutDisplaySize());
MVM_LOG("%p: viewport info has zooms min=%f max=%f default=%f,valid=%d\n", MVM_LOG("%p: viewport info has zooms min=%f max=%f default=%f,valid=%d\n",
@@ -760,10 +766,11 @@ ParentLayerSize MobileViewportManager::GetCompositionSizeWithoutDynamicToolbar()
void MobileViewportManager::UpdateKeyboardHeight( void MobileViewportManager::UpdateKeyboardHeight(
ScreenIntCoord aKeyboardHeight) { ScreenIntCoord aKeyboardHeight) {
if (aKeyboardHeight == mKeyboardHeight) { if (mPendingKeyboardHeight == Some(aKeyboardHeight)) {
return; return;
} }
mKeyboardHeight = aKeyboardHeight;
mPendingKeyboardHeight = Some(aKeyboardHeight);
mInvalidViewport = true; mInvalidViewport = true;
} }

View File

@@ -153,6 +153,8 @@ class MobileViewportManager final : public nsIDOMEventListener,
*/ */
nsRect InitialVisibleArea(); nsRect InitialVisibleArea();
mozilla::ScreenIntCoord GetKeyboardHeight() const { return mKeyboardHeight; }
private: private:
~MobileViewportManager(); ~MobileViewportManager();
@@ -243,6 +245,7 @@ class MobileViewportManager final : public nsIDOMEventListener,
* The software keyboard height. * The software keyboard height.
*/ */
mozilla::ScreenIntCoord mKeyboardHeight; mozilla::ScreenIntCoord mKeyboardHeight;
mozilla::Maybe<mozilla::ScreenIntCoord> mPendingKeyboardHeight;
}; };
#endif #endif

View File

@@ -11418,7 +11418,11 @@ void PresShell::MaybeRecreateMobileViewportManager(bool aAfterInitialization) {
("Created MVM %p (type %d) for URI %s", mMobileViewportManager.get(), ("Created MVM %p (type %d) for URI %s", mMobileViewportManager.get(),
(int)*mvmType, uri ? uri->GetSpecOrDefault().get() : "(null)")); (int)*mvmType, uri ? uri->GetSpecOrDefault().get() : "(null)"));
} }
if (BrowserChild* browserChild = BrowserChild::GetFrom(this)) {
mMobileViewportManager->UpdateKeyboardHeight(browserChild->GetKeyboardHeight());
}
} }
if (aAfterInitialization) { if (aAfterInitialization) {
// Setting the initial viewport will trigger a reflow. // Setting the initial viewport will trigger a reflow.
if (mMobileViewportManager) { if (mMobileViewportManager) {

View File

@@ -247,7 +247,6 @@ nsPresContext::nsPresContext(dom::Document* aDocument, nsPresContextType aType)
mCurAppUnitsPerDevPixel(0), mCurAppUnitsPerDevPixel(0),
mDynamicToolbarMaxHeight(0), mDynamicToolbarMaxHeight(0),
mDynamicToolbarHeight(0), mDynamicToolbarHeight(0),
mKeyboardHeight(0),
mPageSize(-1, -1), mPageSize(-1, -1),
mPageScale(0.0), mPageScale(0.0),
mPPScale(1.0f), mPPScale(1.0f),
@@ -722,8 +721,6 @@ nsresult nsPresContext::Init(nsDeviceContext* aDeviceContext) {
#if defined(MOZ_WIDGET_ANDROID) #if defined(MOZ_WIDGET_ANDROID)
if (IsRootContentDocumentCrossProcess()) { if (IsRootContentDocumentCrossProcess()) {
if (BrowserChild* browserChild = BrowserChild::GetFrom(GetDocShell())) { if (BrowserChild* browserChild = BrowserChild::GetFrom(GetDocShell())) {
mKeyboardHeight = browserChild->GetKeyboardHeight();
if (MOZ_LIKELY(!Preferences::HasUserValue( if (MOZ_LIKELY(!Preferences::HasUserValue(
"layout.dynamic-toolbar-max-height"))) { "layout.dynamic-toolbar-max-height"))) {
mDynamicToolbarMaxHeight = browserChild->GetDynamicToolbarMaxHeight(); mDynamicToolbarMaxHeight = browserChild->GetDynamicToolbarMaxHeight();
@@ -3129,7 +3126,7 @@ void nsPresContext::UpdateDynamicToolbarOffset(ScreenIntCoord aOffset) {
dom::InteractiveWidget interactiveWidget = mDocument->InteractiveWidget(); dom::InteractiveWidget interactiveWidget = mDocument->InteractiveWidget();
if (interactiveWidget == InteractiveWidget::OverlaysContent && if (interactiveWidget == InteractiveWidget::OverlaysContent &&
mKeyboardHeight > 0) { GetKeyboardHeight() > 0) {
// On overlays-content mode, the toolbar offset change should NOT affect // On overlays-content mode, the toolbar offset change should NOT affect
// the visual viewport while the software keyboard is being shown since // the visual viewport while the software keyboard is being shown since
// the toolbar will be positioned somewhere in the middle of the visual // the toolbar will be positioned somewhere in the middle of the visual
@@ -3163,8 +3160,6 @@ void nsPresContext::UpdateDynamicToolbarOffset(ScreenIntCoord aOffset) {
void nsPresContext::UpdateKeyboardHeight(ScreenIntCoord aHeight) { void nsPresContext::UpdateKeyboardHeight(ScreenIntCoord aHeight) {
MOZ_ASSERT(IsRootContentDocumentCrossProcess()); MOZ_ASSERT(IsRootContentDocumentCrossProcess());
mKeyboardHeight = aHeight;
if (!mPresShell) { if (!mPresShell) {
return; return;
} }
@@ -3175,8 +3170,13 @@ void nsPresContext::UpdateKeyboardHeight(ScreenIntCoord aHeight) {
} }
} }
ScreenIntCoord nsPresContext::GetKeyboardHeight() const {
MobileViewportManager* mvm = mPresShell->GetMobileViewportManager();
return mvm ? mvm->GetKeyboardHeight() : ScreenIntCoord(0);
}
bool nsPresContext::IsKeyboardHiddenOrResizesContentMode() const { bool nsPresContext::IsKeyboardHiddenOrResizesContentMode() const {
return mKeyboardHeight == 0 || return GetKeyboardHeight() == 0 ||
mDocument->InteractiveWidget() == InteractiveWidget::ResizesContent; mDocument->InteractiveWidget() == InteractiveWidget::ResizesContent;
} }

View File

@@ -442,7 +442,7 @@ class nsPresContext : public nsISupports, public mozilla::SupportsWeakPtr {
void UpdateKeyboardHeight(mozilla::ScreenIntCoord aHeight); void UpdateKeyboardHeight(mozilla::ScreenIntCoord aHeight);
mozilla::ScreenIntCoord GetKeyboardHeight() const { return mKeyboardHeight; } mozilla::ScreenIntCoord GetKeyboardHeight() const;
/** /**
* Returns true if the software keyboard is hidden or * Returns true if the software keyboard is hidden or
@@ -1247,8 +1247,6 @@ class nsPresContext : public nsISupports, public mozilla::SupportsWeakPtr {
// The maximum height of the dynamic toolbar on mobile. // The maximum height of the dynamic toolbar on mobile.
mozilla::ScreenIntCoord mDynamicToolbarMaxHeight; mozilla::ScreenIntCoord mDynamicToolbarMaxHeight;
mozilla::ScreenIntCoord mDynamicToolbarHeight; mozilla::ScreenIntCoord mDynamicToolbarHeight;
// The software keyboard height.
mozilla::ScreenIntCoord mKeyboardHeight;
// Safe area insets support // Safe area insets support
mozilla::LayoutDeviceIntMargin mSafeAreaInsets; mozilla::LayoutDeviceIntMargin mSafeAreaInsets;
nsSize mPageSize; nsSize mPageSize;