Kodokon kodokon.com

ListView.builder के साथ उच्च-प्रदर्शन वाली सूचियाँ

ListView.builder, ListTile और अपने-अपने विजेट में निकाले गए आइटम की बदौलत हज़ारों आइटम की सूचियाँ बिना किसी धीमेपन के प्रदर्शित करें।

8 मिनट · 3 प्रश्न

इस पाठ को Kodokon में खोलें

एक वास्तविक ऐप लगभग हमेशा सूचियाँ प्रदर्शित करता है: संदेश, उत्पाद, संपर्क। ListView(children: ...) कंस्ट्रक्टर जिसे आप पहले से जानते हैं, अपने सभी चाइल्ड को एक साथ बनाता है - दस आइटम के लिए ठीक है, लेकिन एक हज़ार के लिए विनाशकारी। ListView.builder केवल दृश्य क्षेत्र के पास के आइटम बनाता है, माँग के अनुसार, जैसे-जैसे आप स्क्रॉल करते हैं।

DART
import 'package:flutter/material.dart';

class ContactsScreen extends StatelessWidget {
  const ContactsScreen({super.key, required this.names});

  final List<String> names;

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: const Text('Contacts')),
      body: ListView.builder(
        itemCount: names.length,
        itemBuilder: (context, index) {
          return ListTile(
            leading: const Icon(Icons.person),
            title: Text(names[index]),
          );
        },
      ),
    );
  }
}
केवल दृश्यमान आइटम बनाए जाते हैं, भले ही 10,000 नाम हों।

दो पैरामीटर पूरे तंत्र को संभालते हैं: itemCount आइटम की कुल संख्या घोषित करता है, और itemBuilder किसी दिए गए इंडेक्स पर आइटम बनाता है, केवल तभी जब वह स्क्रीन के पास आता है। हर पंक्ति की सामग्री के लिए, ListTile आपका Material साथी है: leading, title, subtitle और trailing पंक्ति को संरचित करते हैं, और onTap छूने पर इंक रिपल प्रदान करता है। लेकिन जैसे ही कोई आइटम बड़ा होता है, उसे itemBuilder के अंदर फूलने न दें: उसे अपने खुद के विजेट में निकाल लें।

DART
import 'package:flutter/material.dart';

class ContactTile extends StatelessWidget {
  const ContactTile({
    super.key,
    required this.name,
    required this.onTap,
  });

  final String name;
  final VoidCallback onTap;

  @override
  Widget build(BuildContext context) {
    return ListTile(
      leading: CircleAvatar(child: Text(name[0])),
      title: Text(name),
      trailing: const Icon(Icons.chevron_right),
      onTap: onTap,
    );
  }
}
एक सूची आइटम जिसे पुनः प्रयोग योग्य, परीक्षण योग्य विजेट में बदल दिया गया।

एक निकाला गया आइटम अलग से परीक्षण किया जा सकता है, दूसरी स्क्रीनों में पुनः प्रयोग किया जा सकता है, और itemBuilder को साधारण बना देता है। एक बार-बार आने वाली ज़रूरत बची रहती है: विभाजक (separator)। ListView.separated builder की तरह काम करता है, बस एक तीसरे पैरामीटर separatorBuilder के साथ, जिसे आइटम की हर जोड़ी के बीच कॉल किया जाता है - अंतिम तत्व के बाद कभी कोई विभाजक नहीं होता।

DART
import 'package:flutter/material.dart';

class ContactList extends StatelessWidget {
  const ContactList({super.key, required this.names});

  final List<String> names;

  @override
  Widget build(BuildContext context) {
    return ListView.separated(
      itemCount: names.length,
      separatorBuilder: (context, index) {
        return const Divider(height: 1);
      },
      itemBuilder: (context, index) {
        return ContactTile(
          name: names[index],
          onTap: () => debugPrint(names[index]),
        );
      },
    );
  }
}
separatorBuilder आइटम की हर जोड़ी के बीच एक Divider डालता है।

ज्ञान जांच

सुनिश्चित करें कि आपको इस पाठ के मुख्य बिंदु याद हैं।

  1. 500 आइटम की सूची के लिए ListView(children: ...) के बजाय ListView.builder को क्यों प्राथमिकता दें?
    • यह अपने आप आइटम को क्रमबद्ध करता है
    • यह केवल दृश्यमान आइटम बनाता है, माँग के अनुसार
    • यह छवियों को कैश करता है
    • यह अपने आप विभाजक जोड़ता है
  2. कौन सा कंस्ट्रक्टर आइटम की हर जोड़ी के बीच एक विजेट डालता है?
    • ListView.divided
    • ListView.builder
    • ListView.separated
  3. किसी सूची आइटम को उसके अपने विजेट क्लास में निकालने का क्या लाभ है?
    • ListView.builder के कंपाइल होने के लिए यह आवश्यक है
    • यह const को सक्षम करता है, रीबिल्ड को अलग रखता है और पुनः प्रयोग को आसान बनाता है
    • यह सूची को स्क्रॉल करने योग्य बनाता है
    • यह आपको itemCount लिखने से बचाता है