본문 바로가기
ETC/Flutter

[flutter] 무한스크롤 과 새로고침 (pull_to_refresh)

by dkswnkk 2022. 1. 22.

인스타그램, 당근 마켓, 페이스북과 같이 화면을 계속 스크롤하여 데이터를 불러오는 기능은 정보를 공유하는 앱에서 거의 필수적으로 사용되는 기능 중 하나입니다.

오늘은 Flutter에서 이러한 무한 스크롤을 쉽게 구현할 수 있는 방법과 더불어 새로고침 할 수 있는 기능까지 살펴보려고 합니다.

 

 

pull_to_refresh | Flutter Package

a widget provided to the flutter scroll component drop-down refresh and pull up load.

pub.dev

pull_to_refresh

 

위 주소의 pull_to_refresh 패키지를 사용하면 손쉽게 구현할 수 있습니다.

아래 코드는 위 패키지 Readme를 해석하여 주석을 달은 부분이다. 한번 훑어보면 쉽게 이해가 갈 것이라 생각됩니다.

  List<String> items = ["1", "2", "3", "4", "5", "6", "7", "8"];
  RefreshController _refreshController =
      RefreshController(initialRefresh: false);

    //새로고침
    void _onRefresh() async{
    await Future.delayed(Duration(milliseconds: 1000)); //1초를 기다린 후 새로고침한다.
    //이 부분에 새로고침 시 불러올 기능을 구현한다.
    _refreshController.refreshCompleted();
  }

    //무한 스크롤
    void _onLoading() async{
    await Future.delayed(Duration(milliseconds: 1000)); //1초를 기다린 후 새로운 데이터를 불러온다.
    //이부분에 데이터를 계속 불러오는 기능을 구현한다.
    //리스트뷰를 사용한다면 간단한 예로 list.add를 이용하여 데이터를 추가시켜준다.
    _refreshController.loadComplete();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: SmartRefresher(
        enablePullDown: true,	// 아래로 당겨서 새로고침 할 수 있게 할건지의 유무를 결정
        enablePullUp: true,	    // 위로 당겨서 새로운 데이터를 불러올수 있게 할건지의 유무를 결정
        // 이 부분은 'header' 즉 머리뿐으로써, 새로고침시 로딩결과에 따라 어떠한 글자를 띄워 줄지 정의 할 수 있다.
         header: CustomHeader(
            builder: (BuildContext context, RefreshStatus? mode) {
              Widget body;
              if (mode == RefreshStatus.idle) {
                body = Text('');
              } else if (mode == RefreshStatus.refreshing) {
                body = CupertinoActivityIndicator();
              } else {
                body = Text('');
              }
              return Container(
                height: 55.0,
                child: Center(child: body),
              );
            },
          ),
        // 이 부분은 'footer' 번역하면 바닥글이란 의미인데 무한스크롤시 로딩결과에 따라 어떠한 글자를 띄워 줄지를 정의할수있다.
        footer: CustomFooter(	
          builder: (BuildContext context,LoadStatus mode){
            Widget body ;
            if(mode==LoadStatus.idle){
              body =  Text("pull up load");
            }
            else if(mode==LoadStatus.loading){
              body =  CupertinoActivityIndicator();
            }
            else if(mode == LoadStatus.failed){
              body = Text("Load Failed!Click retry!");
            }
            else if(mode == LoadStatus.canLoading){
                body = Text("release to load more");
            }
            else{
              body = Text("No more Data");
            }
            return Container(
              height: 55.0,
              child: Center(child:body),
            );
          },
        ),
        controller: _refreshController,
        onRefresh: _onRefresh,	// 새로고침을 구현한 함수
        onLoading: _onLoading,	// 무한스크롤을 구현한 함수
        child: ListView.builder // 리스트뷰
          itemBuilder: (c, i) => Card(child: Center(child: Text(items[i]))),
          itemExtent: 100.0,
          itemCount: items.length,
        ),
      ),
    );
  }

 

pull_to_refreshListView 뿐만 아니라 GridView와 같은 모든 Scroll Widget에 사용이 가능합니다.

 

댓글