प्रॉडक्ट से जुड़ी खबरें

Jetpack Compose के अप्रैल '26 वर्शन में नया क्या है

पांच मिनट में पढ़ें
Meghan Mehta
डेवलपर एडवोकेट, Android

Jetpack Compose का अप्रैल '26 वर्शन अब स्टेबल है. इस वर्शन में, Compose के मुख्य मॉड्यूल का 1.11 वर्शन (_BOM मैपिंग_ देखें), शेयर किए गए एलिमेंट के डीबग टूल, ट्रैकपैड इवेंट वगैरह शामिल हैं. हमारे पास कुछ ऐसे एपीआई भी हैं जो प्रयोग के तौर पर उपलब्ध हैं. हमें खुशी होगी, अगर आप इन्हें आज़माएं और हमें इनके बारे में सुझाव, शिकायत या राय दें.

आज के वर्शन का इस्तेमाल करने के लिए, अपने Compose BOM वर्शन को यहां अपग्रेड करें:

implementation(platform("androidx.compose:compose-bom:2026.04.01"))

Compose 1.11.0 में हुए बदलाव

टेस्ट में कोरोटीन का एक्ज़ीक्यूशन

हम Compose के टेस्ट टाइमिंग को मैनेज करने के तरीके में एक बड़ा अपडेट कर रहे हैं. Compose 1.10 में बताए गए ऑप्ट-इन की अवधि खत्म हो गई है. अब टेस्ट करने के लिए v2 एपीआई डिफ़ॉल्ट रूप से उपलब्ध हैं. साथ ही, v1 एपीआई को बंद कर दिया गया है. मुख्य बदलाव, डिफ़ॉल्ट टेस्ट डिस्पैचर में हुआ है. v1 एपीआई, UnconfinedTestDispatcher पर काम करते थे. इससे कोरोटीन तुरंत एक्ज़ीक्यूट हो जाते थे. वहीं, v2 एपीआई, StandardTestDispatcher का इस्तेमाल करते हैं. इसका मतलब है कि अब आपके टेस्ट में कोरोटीन लॉन्च होने पर, उसे क्यू में रखा जाता है. साथ ही, वह तब तक एक्ज़ीक्यूट नहीं होता, जब तक वर्चुअल क्लॉक आगे नहीं बढ़ती.

इससे प्रोडक्शन की स्थितियों को बेहतर तरीके से समझा जा सकता है. साथ ही, रेस कंडीशन को आसानी से ठीक किया जा सकता है. इससे आपकी टेस्ट सुइट की परफ़ॉर्मेंस बेहतर होती है और उसमें गड़बड़ियां कम होती हैं.

हमारा सुझाव है कि आप अपनी टेस्ट सुइट को माइग्रेट करें, ताकि आपके टेस्ट, कोरोटीन के स्टैंडर्ड बिहेवियर के मुताबिक काम करें और आने वाले समय में कंपैटबिलटी से जुड़ी समस्याएं न हों. एपीआई मैपिंग और सामान्य समस्याओं को ठीक करने के तरीकों के बारे में जानने के लिए, हमारी माइग्रेशन गाइड देखें.

शेयर किए गए एलिमेंट में सुधार और ऐनिमेशन टूलिंग

हमने शेयर किए गए एलिमेंट और Modifier.animatedBounds के लिए, विज़ुअल डीबग करने के कुछ काम के टूल भी जोड़े हैं. अब यह देखा जा सकता है कि बैकग्राउंड में क्या हो रहा है. जैसे, टारगेट बाउंड, ऐनिमेशन ट्रैजेक्ट्री, और कितने मैच मिले. इससे यह पता लगाना आसान हो जाता है कि ट्रांज़िशन, उम्मीद के मुताबिक क्यों काम नहीं कर रहा है. नए टूलिंग का इस्तेमाल करने के लिए, SharedTransitionLayout को LookaheadAnimationVisualDebugging कंपोज़ेबल के साथ रैप करें. 

LookaheadAnimationVisualDebugging(
    overlayColor = Color(0x4AE91E63),
    isEnabled = true,
    multipleMatchesColor = Color.Green,
    isShowKeylabelEnabled = false,
    unmatchedElementColor = Color.Red,
) {
    SharedTransitionLayout {
        CompositionLocalProvider(
            LocalSharedTransitionScope provides this,
        ) {
            // your content
        }
    }
}

ट्रैकपैड इवेंट

हमने लैपटॉप में बने ट्रैकपैड, टैबलेट के लिए अटैच किए जा सकने वाले ट्रैकपैड या बाहरी/वर्चुअल ट्रैकपैड जैसे ट्रैकपैड के लिए, Compose की सहायता को बेहतर बनाया है. अब सामान्य तौर पर, ट्रैकपैड के बुनियादी इवेंट को PointerType.Mouse इवेंट माना जाएगा. इससे माउस और ट्रैकपैड का बिहेवियर, उपयोगकर्ताओं की उम्मीदों के मुताबिक बेहतर तरीके से काम करेगा. पहले, इन ट्रैकपैड इवेंट को PointerType.Touch के फ़ेक टचस्क्रीन फ़िंगर के तौर पर समझा जाता था. इससे उपयोगकर्ताओं को भ्रमित करने वाला अनुभव मिलता था. उदाहरण के लिए, ट्रैकपैड से क्लिक करके खींचने पर, चुनने के बजाय स्क्रोल होता था. Compose के नए वर्शन में, इन इवेंट के पॉइंटर टाइप को बदलने से, ट्रैकपैड से क्लिक करके खींचने पर अब स्क्रोल नहीं होगा.

हमने प्लैटफ़ॉर्म पर पहचाने जाने वाले, ट्रैकपैड के ज़्यादा मुश्किल जेस्चर के लिए भी सहायता जोड़ी है. इनमें दो उंगलियों से स्वाइप करना और पिंच करना शामिल हैं. ये जेस्चर, एपीआई 34 से उपलब्ध हैं. Modifier.scrollable और Modifier.transformable जैसे कॉम्पोनेंट, इन जेस्चर को अपने-आप पहचान लेते हैं, ताकि ट्रैकपैड के साथ उनका बिहेवियर बेहतर हो.

इन बदलावों से, ट्रैकपैड के लिए, बिल्ट-इन कॉम्पोनेंट का बिहेवियर बेहतर होता है. साथ ही, इसमें टच स्लॉप को हटाया गया है, ड्रैग-एंड-ड्रॉप शुरू करने का ज़्यादा आसान जेस्चर जोड़ा गया है, टेक्स्ट फ़ील्ड में डबल-क्लिक और ट्रिपल-क्लिक से चुनने की सुविधा जोड़ी गई है, और टेक्स्ट फ़ील्ड में डेस्कटॉप स्टाइल वाले कॉन्टेक्स्ट मेन्यू जोड़े गए हैं.

ट्रैकपैड के बिहेवियर को टेस्ट करने के लिए, performTrackpadInput, के साथ नए टेस्टिंग एपीआई उपलब्ध हैं. इनकी मदद से, ट्रैकपैड के साथ इस्तेमाल किए जाने पर, अपने ऐप्लिकेशन के बिहेवियर की पुष्टि की जा सकती है. अगर आपके पास कस्टम जेस्चर डिटेक्टर हैं, तो टचस्क्रीन, माउस, ट्रैकपैड, और स्टाइलस जैसे इनपुट टाइप के लिए, बिहेवियर की पुष्टि करें. साथ ही, पक्का करें कि माउस के स्क्रोल व्हील और ट्रैकपैड के जेस्चर काम करें.

beforeAndAfter.webp

कंपोज़िशन होस्ट डिफ़ॉल्ट (Compose रनटाइम)

हमने HostDefaultProviderLocalHostDefaultProviderHostDefaultKey, और ViewTreeHostDefaultKey जोड़े हैं, ताकि होस्ट-लेवल की सेवाएं सीधे compose-runtime के ज़रिए उपलब्ध कराई जा सकें. इससे लाइब्रेरी को लुकअप के लिए compose-ui पर निर्भर रहने की ज़रूरत नहीं होती. साथ ही, Kotlin Multiplatform को बेहतर तरीके से सहायता मिलती है. इन वैल्यू को कंपोज़िशन ट्री से लिंक करने के लिए, लाइब्रेरी के लेखक compositionLocalWithHostDefaultOf का इस्तेमाल करके, CompositionLocal बना सकते हैं. इससे होस्ट से डिफ़ॉल्ट वैल्यू मिलती हैं.

प्रीव्यू रैपर

Android Studio में कस्टम प्रीव्यू एक नई सुविधा है. इसकी मदद से, यह तय किया जा सकता है कि Compose प्रीव्यू का कॉन्टेंट कैसे दिखेगा.

PreviewWrapperProvider इंटरफ़ेस लागू करके और नया @PreviewWrapper एनोटेशन लागू करके, कस्टम लॉजिक को आसानी से जोड़ा जा सकता है. जैसे, कोई खास Theme लागू करना. इस एनोटेशन को @Composable और @Preview या @MultiPreview के साथ एनोटेट किए गए फ़ंक्शन पर लागू किया जा सकता है. इससे एक सामान्य और इस्तेमाल में आसान समाधान मिलता है. यह समाधान, प्रीव्यू की सभी सुविधाओं के साथ काम करता है और बार-बार लिखे जाने वाले कोड को काफ़ी हद तक कम करता है.

class ThemeWrapper: PreviewWrapper {
    @Composable
    override fun Wrap(content: @Composable (() -> Unit)) {
        JetsnackTheme {
            content()
        }
    }
}

@PreviewWrapperProvider(ThemeWrapper::class)
@Preview
@Composable
private fun ButtonPreview() {
    // JetsnackTheme in effect
    Button(onClick = {}) {
        Text(text = "Demo")
    }
}

बंद की गई और हटाई गई सुविधाएं

  • Compose 1.10 के ब्लॉग पोस्ट में बताए गए तरीके के मुताबिक, हम Modifier.onFirstVisible() को बंद कर रहे हैं. इसके नाम की वजह से अक्सर गलतफ़हमी होती थी. खास तौर पर, लेज़ी लेआउट में स्क्रोल करने के दौरान, यह कई बार ट्रिगर होता था. हमारा सुझाव है कि आप Modifier.onVisibilityChanged() पर माइग्रेट करें. इससे, अपने इस्तेमाल के खास मामले की ज़रूरतों के हिसाब से, दिखने की स्थितियों को मैन्युअल तरीके से ज़्यादा सटीक तरीके से ट्रैक किया जा सकता है.
  • ComposeFoundationFlags.isTextFieldDpadNavigationEnabled फ़्लैग को हटा दिया गया है, क्योंकि अब TextFields के लिए डी-पैड नेविगेशन, डिफ़ॉल्ट रूप से हमेशा चालू रहता है. नए बिहेवियर से यह पक्का होता है कि गेमपैड या टीवी रिमोट से डी-पैड इवेंट, सबसे पहले कर्सर को दी गई दिशा में ले जाएं. फ़ोकस, किसी दूसरे एलिमेंट पर तब ही जा सकता है, जब कर्सर टेक्स्ट के आखिर में पहुंच जाए.

आने वाले एपीआई

Compose 1.12.0 के आने वाले वर्शन में, compileSdk को compileSdk 37 पर अपग्रेड किया जाएगा. साथ ही, AGP 9 और Compose पर निर्भर रहने वाले सभी ऐप्लिकेशन और लाइब्रेरी के लिए, यह ज़रूरी होगा. हमारा सुझाव है कि रिलीज़ किए गए नए वर्शन के साथ अप-टू-डेट रहें, क्योंकि Compose, Android की नई सुविधाओं का ऐक्सेस देने के लिए, नए compileSdks को तुरंत अपनाता है. अलग-अलग एपीआई लेवल के लिए, AGP का कौनसा वर्शन काम करता है, इस बारे में ज़्यादा जानकारी के लिए, यहां दस्तावेज़ देखें. 

Compose 1.11.0 में, इन एपीआई को @Experimental के तौर पर पेश किया गया है. हमें खुशी होगी, अगर आप अपने ऐप्लिकेशन में इनका इस्तेमाल करें और हमें इनके बारे में सुझाव, शिकायत या राय दें. ध्यान दें कि @Experimental APIs को शुरुआती आकलन और सुझाव, शिकायत या राय के लिए उपलब्ध कराया जाता है. आने वाले वर्शन में इनमें बड़े बदलाव किए जा सकते हैं या इन्हें हटाया जा सकता है.

स्टाइल (प्रयोग के तौर पर उपलब्ध)

हम स्टाइलिंग के लिए, एक नया एक्सपेरिमेंटल फ़ाउंडेशन एपीआई पेश कर रहे हैं. स्टाइल एपीआई, कॉम्पोनेंट के विज़ुअल एलिमेंट को कस्टमाइज़ करने का एक नया तरीका है. इसे पारंपरिक तौर पर मॉडिफ़ायर की मदद से किया जाता था. इसे, स्टाइल की जा सकने वाली प्रॉपर्टी के स्टैंडर्ड सेट को, स्टेट पर आधारित आसान स्टाइलिंग और ऐनिमेटेड ट्रांज़िशन के साथ उपलब्ध कराकर, ज़्यादा बेहतर और आसान तरीके से कस्टमाइज़ करने के लिए डिज़ाइन किया गया है. इस नए एपीआई से, हमें परफ़ॉर्मेंस के मामले में बेहतर नतीजे मिल रहे हैं. स्टाइल एपीआई के स्टेबल होने के बाद, हम मटीरियल कॉम्पोनेंट में स्टाइल को शामिल करने की योजना बना रहे हैं.

प्रेस किए गए स्टेट स्टाइल बैकग्राउंड को बदलने का एक बुनियादी उदाहरण:

@Composable
fun LoginButton(modifier: Modifier = Modifier) {
    Button(
        onClick = {
            // Login logic
        },
        modifier = modifier,
        style = {
            background(
                Brush.linearGradient(
                    listOf(lightPurple, lightBlue)
                )
            )
            width(75.dp)
            height(50.dp)
            textAlign(TextAlign.Center)
            externalPadding(16.dp)

            pressed {
                background(
                    Brush.linearGradient(
                        listOf(Color.Magenta, Color.Red)
                    )
                )
            }
        }
    ){
        Text(
            text = "Login",
        )
    }
}
styles.webp

दस्तावेज़ देखें और गड़बड़ियों की शिकायत यहां करें.

MediaQuery (प्रयोग के तौर पर उपलब्ध)

नया mediaQuery एपीआई, आपके यूज़र इंटरफ़ेस (यूआई) को उसके एनवायरमेंट के हिसाब से अडजस्ट करने का एक डिक्लेरेटिव और परफ़ॉर्म करने वाला तरीका है. यह, जटिल जानकारी को फ़ेच करने की प्रोसेस को UiMediaScope में आसान शर्तों में बदलता है. इससे, ज़रूरत पड़ने पर ही रीकंपोज़िशन होता है.

डिवाइस की क्षमताओं (जैसे, कीबोर्ड टाइप और पॉइंटर प्रिसिशन) से लेकर, कॉन्टेक्चुअल स्टेट (जैसे, विंडो साइज़ और पॉस्चर) तक, एनवायरमेंटल सिग्नल की अलग-अलग रेंज के लिए सहायता उपलब्ध होने से, रिस्पॉन्सिव अनुभव बनाए जा सकते हैं. derivedMediaQuery की मदद से, परफ़ॉर्मेंस को बेहतर बनाया जा सकता है. इससे, ज़्यादा फ़्रीक्वेंसी वाले अपडेट को मैनेज किया जा सकता है. साथ ही, स्कोप को बदलने की सुविधा से, हार्डवेयर कॉन्फ़िगरेशन में टेस्ट और प्रीव्यू को आसानी से देखा जा सकता है. पहले, डिवाइस की कुछ प्रॉपर्टी का ऐक्सेस पाने के लिए — जैसे, कोई डिवाइस टेबलटॉप मोड में है या नहीं — आपको ऐसा करने के लिए, बहुत सारा बॉयलरप्लेट लिखना पड़ता था: 

@Composable
fun isTabletopPosture(
    context: Context = LocalContext.current
): Boolean {
    val windowLayoutInfo by
        WindowInfoTracker
            .getOrCreate(context)
            .windowLayoutInfo(context)
            .collectAsStateWithLifecycle(null)

    return windowLayoutInfo.displayFeatures.any { displayFeature ->
        displayFeature is FoldingFeature &&
            displayFeature.state == FoldingFeature.State.HALF_OPENED &&
            displayFeature.orientation == FoldingFeature.Orientation.HORIZONTAL
    }
}

@Composable
fun VideoPlayer() {
    if(isTabletopPosture()) {
        TabletopLayout()
    } else {
        FlatLayout()
    }
}

अब UIMediaQuery की मदद से, डिवाइस की प्रॉपर्टी के बारे में क्वेरी करने के लिए, mediaQuery सिंटैक्स जोड़ा जा सकता है. जैसे, कोई डिवाइस टेबलटॉप मोड में है या नहीं:

@OptIn(ExperimentalMediaQueryApi::class)
@Composable
fun VideoPlayer() {
    if (mediaQuery { windowPosture == UiMediaScope.Posture.Tabletop }) {
        TabletopLayout()
    } else {
        FlatLayout()
    }
}

दस्तावेज़ देखें और गड़बड़ियों की शिकायत यहां करें.

Grid (प्रयोग के तौर पर उपलब्ध)

Grid, Jetpack Compose में, दो डाइमेंशन वाले जटिल लेआउट बनाने के लिए एक नया और असरदार एपीआई है. Row और Column, लीनियर डिज़ाइन के लिए बेहतरीन हैं. वहीं, Grid से आपको स्क्रीन-लेवल के आर्किटेक्चर और जटिल कॉम्पोनेंट के लिए स्ट्रक्चरल कंट्रोल मिलता है. इसके लिए, स्क्रोल की जा सकने वाली सूची की ज़रूरत नहीं होती. Grid की मदद से, ट्रैक, गैप, और सेल का इस्तेमाल करके अपना लेआउट तय किया जा सकता है. इसमें, Dp, प्रतिशत, इंट्रिंसिक कॉन्टेंट साइज़, और फ़्लेक्सिबल "Fr" यूनिट जैसे साइज़िंग के विकल्प मिलते हैं.

@OptIn(ExperimentalGridApi::class)
@Composable
fun GridExample() {
    Grid(
        config = {
            repeat(4) { column(0.25f) }
            repeat(2) { row(0.5f) }
            gap(16.dp)
        }
    ) {
        Card1(modifier = Modifier.gridItem(rowSpan = 2)
        Card2(modifier = Modifier.gridItem(colmnSpan = 3)
        Card3(modifier = Modifier.gridItem(columnSpan = 2)
        Card4()
    }
}

आइटम को अपने-आप प्लेस किया जा सकता है या सटीक तरीके से प्लेस करने के लिए, उन्हें एक से ज़्यादा पंक्तियों और कॉलम में फैलाया जा सकता है. सबसे अच्छी बात यह है कि यह बहुत अडैप्टिव है. डिवाइस की स्थितियों (जैसे, टेबलटॉप मोड या ओरिएंटेशन में बदलाव) के हिसाब से, ग्रिड ट्रैक और स्पैन को डाइनैमिक तरीके से फिर से कॉन्फ़िगर किया जा सकता है. इससे, अलग-अलग फ़ॉर्म फ़ैक्टर में आपका यूज़र इंटरफ़ेस (यूआई) बेहतर दिखता है.

Grid.gif

दस्तावेज़ देखें और गड़बड़ियों की शिकायत यहां करें. 

FlexBox (प्रयोग के तौर पर उपलब्ध)

FlexBox, हाई परफ़ॉर्मेंस और अडैप्टिव यूज़र इंटरफ़ेस (यूआई) के लिए डिज़ाइन किया गया एक लेआउट कंटेनर है. यह, उपलब्ध कंटेनर डाइमेंशन के आधार पर, आइटम के साइज़ और स्पेस डिस्ट्रिब्यूशन को मैनेज करता है.यह, रैपिंग (wrap) और आइटम के मल्टी-ऐक्सिस अलाइनमेंट (justifyContent, alignItems, alignContent) जैसे जटिल टास्क को मैनेज करता है. इससे आइटम को कंटेनर में फ़िट करने के लिए, बड़ा (grow) या छोटा (shrink) किया जा सकता है. 

@OptIn(ExperimentalFlexBoxApi::class)
fun FlexBoxWrapping(){
    FlexBox(
        config = {
            wrap(FlexWrap.Wrap)
            gap(8.dp)
        }
    ) {
        RedRoundedBox()
        BlueRoundedBox()
        GreenRoundedBox(modifier = Modifier.width(350.dp).flex { grow(1.0f) })
        OrangeRoundedBox(modifier = Modifier.width(200.dp).flex { grow(0.7f) })
        PinkRoundedBox(modifier = Modifier.width(200.dp).flex { grow(0.3f) })
    }
}
AnimationGif.gif

दस्तावेज़ देखें और गड़बड़ियों की शिकायत यहां करें.

SlotTable का नया वर्शन (प्रयोग के तौर पर उपलब्ध)

हमने SlotTable का नया वर्शन पेश किया है. यह वर्शन, इस रिलीज़ में डिफ़ॉल्ट रूप से बंद है. SlotTable, इंटरनल डेटा स्ट्रक्चर है. इसका इस्तेमाल, Compose रनटाइम, कंपोज़िशन हैरारकी की स्थिति को ट्रैक करने, इनवैलिडेशन/रीकंपोज़िशन को ट्रैक करने, याद रखी गई वैल्यू को सेव करने, और रनटाइम में कंपोज़िशन के सभी मेटाडेटा को ट्रैक करने के लिए करता है. इस नए वर्शन को, परफ़ॉर्मेंस को बेहतर बनाने के लिए डिज़ाइन किया गया है. खास तौर पर, रैंडम बदलावों के लिए.

SlotTable के नए वर्शन को आज़माने के लिए, ComposeRuntimeFlags.isLinkBufferComposerEnabled को चालू करें. 

आज से ही कोडिंग शुरू करें!

Jetpack Compose में कई नए और बेहतरीन एपीआई उपलब्ध हैं. साथ ही, आने वाले समय में और भी एपीआई उपलब्ध होंगे. इसलिए, Jetpack Compose पर माइग्रेट करने के लिए यह सबसे सही समय है.हमेशा की तरह, हमें आपके सुझाव, शिकायत या राय और सुविधाओं के अनुरोधों की अहमियत है. खास तौर पर, @Experimental सुविधाओं के बारे में, जो अब भी डेवलपमेंट में हैं. कृपया इन्हें यहां सबमिट करें. कंपोज़िंग के लिए शुभकामनाएं!

लेखक:

पढ़ना जारी रखें