Skip to content

[Paywalls V2] Ignore top safe area edges for image#4744

Merged
joshdholtz merged 5 commits into
mainfrom
paywalls-v2/ignore-top-edges-for-image
Jan 30, 2025
Merged

[Paywalls V2] Ignore top safe area edges for image#4744
joshdholtz merged 5 commits into
mainfrom
paywalls-v2/ignore-top-edges-for-image

Conversation

@joshdholtz

@joshdholtz joshdholtz commented Jan 30, 2025

Copy link
Copy Markdown
Member

Motivation

Be smart about when and where to ignore safe area edges so header images expand all the way to the top edge.

Description

  1. In the ViewModelFactory, find if the first non-container type component is an image
    • If we find one, also pair it with its parent if its a ZStack
      • We need this so that we can apply safe area insets to the non-images in the ZStack so they stay pushed down
      • We add a new boolean into the StackViewModel of the containing ZStack that we need to apply safe area inset padding
  2. If we found that an image is first:
    • Apply .edgesIgnoringSafeArea(.top) to the entire paywall contents
    • Send the value of the safe area insets as an environment variable
  3. When rendering the paywall, we apply the safe area insets into the ZStack components if needed so they stay pushed down

👉 See #4745 for the Paywall Tester changes

Screen.Recording.2025-01-29.at.5.53.51.PM.mov

@joshdholtz joshdholtz changed the title Ignore top safe area edges for image [Paywalls V2] Ignore top safe area edges for image Jan 30, 2025
@joshdholtz joshdholtz requested review from a team January 30, 2025 00:46

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ignoring edges on all views being used as the background

@joshdholtz joshdholtz marked this pull request as ready for review January 30, 2025 02:26
@joshdholtz joshdholtz force-pushed the paywalls-v2/ignore-top-edges-for-image branch from 0ccb313 to b73ce2f Compare January 30, 2025 03:43

@ajpallares ajpallares left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good to me! Just some very very small comments

Comment on lines +79 to +80
// Applies a top padding to mimmic safe area insets
// This was designed to be applied to the

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Small nit: complete explanatory comment

ComponentsView(componentViewModels: self.viewModel.viewModels, onDismiss: self.onDismiss)
ComponentsView(
componentViewModels: self.viewModel.viewModels,
ignoreSafeArea: self.viewModel.shouldApplySafeAreaInset,

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The parameter name ignoreSafeArea seems contradictory with sending self.viewModel.shouldApplySafeAreaInset

Comment thread RevenueCatUI/Templates/V2/PaywallsV2View.swift

@tonidero tonidero left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM! Just a couple cases I was thinking about... The edge case might be acceptable for now but I'm wondering if the design of having an image at the top of the paywall but not as a header would be affected with this...

// If the first view in the first stack is an image,
// we will ignore safe area pass the safe area insets in to environment
// If the image is in a ZStack, the ZStack will push non-images
// down with the inset

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Talking about an edge case here but what happens if the parent of the image (being the first view within the first stack) is an HStack with an image + some text to the side? I imagine in that situation we might not want to ignore the safe area... So maybe this should only be done if the parent of the image is either a VStack or a ZStack?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good point! I just changed the logic so that the image needs to have a width of fill for this to work so... I think that should cover the HStack scenario 🤔

Comment thread RevenueCatUI/Templates/V2/PaywallsV2View.swift

@JayShortway JayShortway left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this is a great and pragmatic solution! 💪

Comment thread RevenueCatUI/Templates/V2/Components/ComponentsView.swift Outdated
Comment thread RevenueCatUI/Templates/V2/Components/Root/RootViewModel.swift
Comment thread RevenueCatUI/Templates/V2/ViewModelHelpers/ViewModelFactory.swift Outdated
Comment thread RevenueCatUI/Templates/V2/Components/ComponentsView.swift Outdated
@joshdholtz joshdholtz merged commit ca12ad7 into main Jan 30, 2025
@joshdholtz joshdholtz deleted the paywalls-v2/ignore-top-edges-for-image branch January 30, 2025 11:04
@ferrannp

ferrannp commented Mar 25, 2025

Copy link
Copy Markdown

@joshdholtz any ideas on how to control the X (close button) position on top-right of a background image in this case? It seems to be placed differently in your video too. It seems hard to add it on the top-right corner for these devices:

  • iPhone with notch or dynamic island
  • iPhone SE
  • Android

(to be in the same position).

Illustration:

Screenshot 2025-03-25 at 23 55 53

Do I need a new issue? I guess this could be solved by telling to a Button/Stack if it should apply top inset or not.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

6 participants