Jetpack Compose Samples

repository·main·Indexed 12 days ago

https://github.com/android/compose-samples

A collection of Android Studio projects demonstrating Jetpack Compose APIs, architectures, and design patterns. Includes samples such as Jetcaster (advanced Redux-style architecture, Wear OS, and Room), JetNews (Material app with Glance AppWidgets and UI testing), Jetsnack (custom design systems and layouts), JetLagged (custom graphics and AGSL shaders), and Reply (adaptive design for foldables and tablets using WindowSizeClass).

Tokens
4.1K
Snippets
5
Records
29
Agent score
97%

What's inside Jetpack Compose Samples

  1. Explore JetLagged features and implementation patterns

    main

    The JetLagged sample demonstrates several advanced Jetpack Compose capabilities that developers can use as reference implementations:

    • Custom Layouts: Implementation of non-standard UI positioning and measurement.
    • Graphics: Use of Custom Paths, Gradients, and AGSL (Android Graphics Shading Language) shaders.
    • Animations: Complex UI transitions and state-driven motion.
    • Complexity: A medium-complexity architecture suitable for studying real-world app structure.
  2. Browse Jetpack Compose Samples by use case

    main

    This repository contains several individual Android Studio projects, each demonstrating different levels of complexity and specific Compose APIs:

    • JetNews: Medium complexity. Demonstrates a typical Material app with real-world architecture, light/dark themes, resource loading, and UI testing.
    • Jetchat: Low complexity. Focuses on UI state patterns, text input, Material Design 3, dynamic color, and integration with Architecture Components (Navigation, Fragments, LiveData, ViewModel).
    • Jetsnack: Medium complexity. Showcases a custom design system, custom layouts, and animations.
    • Jetcaster: Advanced. Features a Redux-style architecture, dynamic theming based on artwork, WindowInsets support, Coroutines, and Room storage.
    • Reply: Medium complexity. Focuses on adaptive design for mobile, tablets, and foldables using Material 3.
    • JetLagged: Showcases custom layouts and graphics using Paths for graphs.
  3. Understand Jetcaster data layer and podcast fetching

    main

    The data layer manages podcast information dynamically from RSS feeds.

    Data Flow:

    1. Fetching: PodcastFetcher uses OkHttp to fetch RSS feeds and Rome to parse them.
    2. Repository: PodcastRepository coordinates the fetching process.
    3. Storage: Parsed entities are stored in a local Room database (JetcasterDatabase) using specialized stores: PodcastStore, EpisodeStore, and CategoryStore.

    Key Features:

    • Following Podcasts: Implemented via the PodcastFollowedEntry entity and PodcastStore functions (followPodcast(), unfollowPodcast()).
    • Date/Time: Uses JDK 8 date and time APIs with DateTimeTypeConverters for Room compatibility.
  4. Understand the data layer architecture

    main

    The app follows the Repository pattern for data management:

    • Data Providers: Uses static local providers for email (LocalEmailsDataProvider) and account (LocalAccountsDataProvider) data.
    • Repository: The EmailRepository emits a Flow of emails from the local data source.
    • ViewModel: The ReplyHomeViewModel observes the repository's flow within the viewModelScope and exposes the data to the ReplyApp composable via a StateFlow.
  5. Implement adaptive content layouts (Inbox and Detail)

    main

    The Inbox screen adapts its content type based on the available screen real estate:

    • Compact/Small screens: Displays an 'Inbox only' view.
    • Medium/Large screens: Displays 'Inbox and thread detail' together, switching between a list-only view and a list-and-detail view depending on the size.
  6. Implement a custom design system in Jetpack Compose

    main

    Jetsnack demonstrates how to implement a bespoke color system that does not rely on Material color theming. The implementation follows these patterns:

    1. Define a Color Palette: Create a class like JetsnackColorPalette to model your specific color system.
    2. Use CompositionLocal: Use an Ambient (via compositionLocalOf) such as JetsnackColorAmbient to hold the current color set.
    3. Provide Colors: Create a composable function like ProvideJetsnackColors that uses CompositionLocalProvider to provide the JetsnackColorPalette to the UI tree.
    4. Access Colors: Use a singleton object like JetsnackTheme to provide convenient, type-safe access to the current theme colors throughout the app.
    5. Wrap Material Components: Customize existing Material components (e.g., JetsnackButton) to consume your custom color system instead of the default Material colors.

    Note: Even when using a custom color system, you can still leverage Material's shape and typography theming.

  7. Implement adaptive design with WindowSizeClass and WindowLayoutInfo

    main

    The Reply sample demonstrates how to build adaptive apps for mobile, tablets, and foldables using two key mechanisms:

    1. Dynamic window resizing: Use WindowSizeClass to detect the current device size and configuration. This allows the UI to observe and react to changes like orientation shifts or device unfolding.
    2. Dynamic fold detection: Use WindowLayoutInfo to observe display features, including Folding Postures, in real-time. This helps adjust the UI when the fold state changes.
  8. Implement AppWidgets using Glance in Jetnews

    main

    The com.example.jetnews.glance package demonstrates how to use the Glance library to write Compose-style code for AppWidgets. Key capabilities shown include:

    • Layout: Using Row, Column, and LazyColumn to arrange widget content.
    • Data Integration: Using an existing app repository to load data and perform widget updates.
    • Scheduling: Configuring android:updatePeriodMillis for periodic refreshes.
    • Theming: Using androidx.glance:glance-material3 with GlanceTheme to implement custom color schemes and support dynamic colors.
    • Assets: Tinting Image components to match the current color scheme.
    • Interactions: Launching an activity on click using actionStartActivity.
  9. How Jetcaster's Redux-style architecture works

    main

    Jetcaster uses a Redux-style architecture for its UI. Each screen is associated with its own ViewModel, which manages the view state through a single StateFlow.

    Key components of this pattern:

    1. ViewModel: Responsible for subscribing to data streams and exposing functions for the UI to trigger events.
    2. ViewState: An @Immutable data class containing the complete state for a specific screen.
    3. UI Observation: The Compose UI observes the StateFlow using collectAsStateWithLifecycle() to ensure lifecycle-aware state updates.

    This pattern is applied consistently across the Home, Discover, and Podcast Category screens.

    val viewModel: HomeViewModel = viewModel()
    val viewState by viewModel.state.collectAsStateWithLifecycle()
  10. Understand Jetsnack data modeling and imagery

    main

    Jetsnack uses the following approach for data and assets:

    • Domain Models: Data types are defined in the model package.
    • Fake Repositories: Static sample data is exposed via fake Repo objects for testing and demonstration.
    • Image Loading: Imagery is loaded using the Coil library.
  11. Use custom layouts and gradients

    main

    Jetsnack uses custom Layout implementations to achieve complex UI designs. Key examples include:

    • Collapsing Layouts: Using CollapsingImageLayout for specialized scrolling effects.
    • Custom Positioning: Using custom layouts like SearchCategory to position images and text items in non-standard ways.
    • Animated Navigation: Using JetsnackBottomNavLayout for bottom navigation that animates item widths.

    For visual styling, Jetsnack utilizes a Gradient utility providing various Modifiers to apply complex color transitions to components.