Generalize PaywallComponentsScaffold for workflow reuse#3417
Conversation
1371e22 to
f0bc422
Compare
7b4fbec to
f3f173e
Compare
f0bc422 to
0c815c2
Compare
dc3b6e9 to
4991932
Compare
0c815c2 to
bb79d4e
Compare
4991932 to
02501fc
Compare
080ad91 to
8c45648
Compare
Codecov Report✅ All modified and coverable lines are covered by tests. Additional details and impacted files@@ Coverage Diff @@
## main #3417 +/- ##
=======================================
Coverage 79.45% 79.45%
=======================================
Files 362 362
Lines 14539 14539
Branches 1976 1976
=======================================
Hits 11552 11552
Misses 2190 2190
Partials 797 797 ☔ View full report in Codecov by Sentry. 🚀 New features to boost your workflow:
|
6127140 to
94a6c34
Compare
8c45648 to
553bfb7
Compare
e4e3bc9 to
fbf8377
Compare
PaywallComponentsScaffold for workflow reuse
51e1e9f to
ff264e9
Compare
d61577a to
e83165a
Compare
3abb26a to
0c63590
Compare
0a37d7a to
9a6d39b
Compare
There was a problem hiding this comment.
Cursor Bugbot has reviewed your changes and found 1 potential issue.
❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, have a team admin enable autofix in the Cursor dashboard.
Reviewed by Cursor Bugbot for commit 9a6d39b4b9fc71be94612be240e5b7e4ceabb338. Configure here.
| * Returns `false` when the root stack already scrolls vertically (overflow = SCROLL on a vertical | ||
| * dimension), because two vertical scroll modifiers on the same axis crash at runtime. | ||
| */ | ||
| @JvmSynthetic |
There was a problem hiding this comment.
Redundant @JvmSynthetic on file-level synthetic function
Low Severity
The @JvmSynthetic annotation on shouldWrapMainContentInVerticalScroll is redundant because the file already has @file:JvmSynthetic on line 1, which applies to all top-level declarations. Additionally, the function is internal, so the annotation provides no additional value.
Reviewed by Cursor Bugbot for commit 9a6d39b4b9fc71be94612be240e5b7e4ceabb338. Configure here.
| ) { | ||
| WithOptionalBackgroundOverlay(state, background = background) { | ||
| Column { | ||
| HeaderOverlayLayout( | ||
| state = state, | ||
| modifier = Modifier.weight(1f), | ||
| ) { | ||
| // Child 0: caller-supplied main content (scrollable body or slide container). | ||
| // Child 0: caller-supplied main content (scrollable body). |
There was a problem hiding this comment.
isn't this the slide container now? based on the pr desc
facumenzella
left a comment
There was a problem hiding this comment.
thanks for splitting into small chunks 💪
2c45061 to
46bf10d
Compare
9a6d39b to
6a0bb78
Compare
46bf10d to
59037fa
Compare
6a0bb78 to
313c2c8
Compare
950054c to
a661ac3
Compare
313c2c8 to
ac38b8f
Compare
PaywallComponentsScaffold now accepts optional headerState, backgroundState, and renderStickyFooter parameters (all default to single-page behaviour) so LoadedWorkflowPaywall can pin a stable header during a slide transition, opt out of the scaffold-level background, and skip the sticky footer when each step renders its own. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The property was returning the live ArrayDeque reference, letting callers observe future mutations through the List handle. toList() produces an actual snapshot consistent with the property name. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
ac38b8f to
1cd2187
Compare
**This is an automatic release.** ## RevenueCat SDK ### ✨ New Features * Add optional support for setting obfuscated account id to product changes (RevenueCat#3428) via Mark Villacampa (@MarkVillacampa) ## RevenueCatUI SDK ### Paywallv2 #### ✨ New Features * Add slide transition to workflow paywalls (RevenueCat#3418) via Cesar de la Vega (@vegaro) * Workflow state & ViewModel infrastructure (RevenueCat#3416) via Cesar de la Vega (@vegaro) #### 🐞 Bugfixes * Fix paywall layout direction for RTL locale overrides (PWENG-39) (RevenueCat#3425) via Monika Mateska (@MonikaMateska) * Apply ripple shape clip on a sibling Box to avoid clipping content (RevenueCat#3395) via Toni Rico (@tonidero) ### 🔄 Other Changes * build(deps): bump fastlane-plugin-revenuecat_internal from `21e02ec` to `af7bb5c` (RevenueCat#3442) via dependabot[bot] (@dependabot[bot]) * Abstract workflow page transition animation behind sealed class (RevenueCat#3430) via Cesar de la Vega (@vegaro) * Add `single_step_fallback_id` field to `PublishedWorkflow` (RevenueCat#3436) via Cesar de la Vega (@vegaro) * build(deps): bump fastlane-plugin-revenuecat_internal from `2d11430` to `21e02ec` (RevenueCat#3429) via dependabot[bot] (@dependabot[bot]) * Generalize `PaywallComponentsScaffold` for workflow reuse (RevenueCat#3417) via Cesar de la Vega (@vegaro) * perf: pre-warm workflow paywall step states off-thread (RevenueCat#3420) via Cesar de la Vega (@vegaro) * Update baseline profiles (RevenueCat#3427) via RevenueCat Git Bot (@RCGitBot) * build(deps): bump fastlane-plugin-revenuecat_internal from `d24ab26` to `2d11430` (RevenueCat#3426) via dependabot[bot] (@dependabot[bot]) * Replace unauthenticated SDKMAN install with SHA-pinned orb command (RevenueCat#3407) via Rick (@rickvdl) * Auto load paywall in paywall tester via local.properties (RevenueCat#3405) via Cesar de la Vega (@vegaro) <!-- CURSOR_SUMMARY --> --- > [!NOTE] > **Low Risk** > Low risk: this is a version/release cut that mainly updates version strings, changelogs, and doc deployment targets with no functional logic changes beyond version identifiers. > > **Overview** > Cuts the `10.4.0` release by removing `-SNAPSHOT` across the project (core `VERSION_NAME`, `Config.frameworkVersion`, sample/test app dependency versions, and the root `.version` file). > > Updates release collateral and publishing to point at `10.4.0`, including changelogs (`CHANGELOG.md`/`CHANGELOG.latest.md`), docs redirect (`docs/index.html`), and the CircleCI `docs-deploy` S3 sync path (from `10.4.0-SNAPSHOT` to `10.4.0`). > > <sup>Reviewed by [Cursor Bugbot](https://cursor.com/bugbot) for commit f7b3604. Bugbot is set up for automated code reviews on this repo. Configure [here](https://www.cursor.com/dashboard/bugbot).</sup> <!-- /CURSOR_SUMMARY -->



Motivation
Workflow paywalls (multi-step) and single-page component paywalls share the same chrome — background, bottom sheet, fixed header overlay, and sticky footer — but differ in how the body is rendered (a single column vs. two sliding columns). Today
LoadedPaywallComponentsowns all of that scaffolding inline, so a workflow renderer would have to either duplicate it or wrap it awkwardly.Description
Refactors
PaywallComponentsScaffoldinto a pure layout primitive with three composable slots and a narrow value type for the painted background:state— primary state, used for the bottom sheet, locale, and the layout pass that measures the header overlay's height.background— narrowBackgroundStyle?instead of a wholePaywallState.Loaded.Components. Defaults torememberBackgroundStyle(state.background). Passnullto skip background painting (workflow paints per-step backgrounds inside its sliding surfaces).headerContent— composable slot for the fixed header overlay. Standard caller derives it fromstate.header; workflow caller derives it from a workflow-selected step state to keep the from-step's header visible during a backward swipe. The slot is rendered as child 1 ofHeaderOverlayLayout, which still measures it first to setstate.headerHeightPxfor body padding.footerContent— composable slot for the sticky footer. Standard caller derives it fromstate.stickyFooter; workflow caller passes nothing because each step renders its own footer that slides with the body.mainContent— the scrollable body.Click handling and component-interaction tracking are no longer scaffold concerns — the scaffold has nothing to dispatch from once header/footer rendering moves to caller-owned slots, so
clickHandler/componentInteractionTrackerparameters are dropped. Each caller constructs its ownonClickand threads it through the slot lambdas.Pure refactor — single-page behavior is unchanged. Workflow PRs downstream consume the slots.
Checklist
Note
Medium Risk
Refactors paywall Compose scaffolding and background application, which could subtly affect layout/scrolling behavior across paywalls despite being intended as behavior-preserving. Adds a small workflow navigation snapshot change that reduces mutation risk.
Overview
Refactors
PaywallComponentsScaffoldinto a reusable layout primitive with explicitmainContent, optionalheaderContent/footerContentslots, and an optionalBackgroundStyle?so workflow paywalls can reuse the same chrome while controlling header/footer rendering and background painting.Moves click handling/interaction tracking out of the scaffold into
LoadedPaywallComponents, addsshouldWrapMainContentInVerticalScroll(...)helper (with new unit tests) to avoid double-verticalScrollcrashes, and makesWorkflowNavigator.backStackSnapshotreturn an immutable list copy (toList()) instead of exposing the deque.Reviewed by Cursor Bugbot for commit 1cd2187. Bugbot is set up for automated code reviews on this repo. Configure here.