Skip to content

Free trial timeline paywall for Jetpack Compose

TrialTimelinePaywall is design 3 of M3 Expressive Paywall. Explains exactly what happens during the trial: full access today, a reminder before it ends, and the day billing starts. The timeline describes the first plan that has a trialText, and fades when the user selects a plan without a trial.

Trial timeline paywall, light theme
Light
Trial timeline paywall, dark theme
Dark
implementation("com.github.sanikantv:m3-expressive-paywall:v1.0.0")
  • You offer a free trial and want more people to start it with confidence.
  • You want to reduce “I forgot to cancel” refund requests.
TrialTimelinePaywall(
plans = listOf(Sample.yearly, Sample.monthly),
legal = Sample.legal,
onPurchase = buy,
onRestore = restore,
onClose = close,
)
TrialTimelinePaywall(
plans = listOf(Sample.yearly.copy(trialText = "14-day free trial")),
legal = Sample.legal,
onPurchase = buy,
onRestore = restore,
onClose = close,
steps = defaultTrialSteps(Sample.yearly, trialDays = 14, reminderDay = 12),
)
val steps = listOf(
TrialStep("Today", "Every Pro feature unlocks right away.", PaywallIcons.LockOpen),
TrialStep("Day 5", "We email you a reminder. No surprise charges.", PaywallIcons.Bell),
TrialStep("Day 7", "Your plan starts at ${Sample.yearly.price} ${Sample.yearly.period}.", PaywallIcons.Calendar),
)
TrialTimelinePaywall(
plans = listOf(Sample.yearly, Sample.monthly),
legal = Sample.legal,
onPurchase = buy,
onRestore = restore,
onClose = close,
steps = steps,
)
Parameter Type Default Description
plans List<PaywallPlan> required Plans to offer. The first plan with trialText drives the timeline.
legal PaywallLegal required Terms and Privacy URLs for the footer links.
onPurchase (PaywallPlan) -> Unit required Called with the selected plan when the button is tapped. Start your billing flow here.
onRestore () -> Unit required Called from the Restore link.
onClose () -> Unit required Called from the close button.
modifier Modifier Modifier Applied to the paywall’s root.
title String “How your free trial works” Headline.
subtitle String? “No surprises. We remind you before you pay.” Line under the headline.
steps List<TrialStep> defaultTrialSteps(trialPlan) Timeline steps. The default is Today, Day 5 and Day 7.
initialPlanId String? null Plan to preselect. Defaults to the first plan with a trial.

defaultTrialSteps(plan: PaywallPlan, trialDays: Int = 7, reminderDay: Int = trialDays - 2): List<TrialStep> builds the three default steps from the plan’s price and period. It is @Composable because it reads the translated strings.

Full signature: TrialTimelinePaywall in the API reference.

Pass your own TrialStep list to change the copy or icons. Keep the last step’s price identical to the plan’s price; the footer repeats it.

  • Timeline icons are decorative; the step title and description carry the meaning for TalkBack.
  • The selected plan is announced as a radio option.
  • Promising a reminder you never send. If the timeline says Day 5, schedule that notification (for example with WorkManager).
  • A trialText that disagrees with the store’s real trial length.

Built by Sanikant. Set in Google Sans Flex (SIL Open Font License). Not affiliated with Google.