flutter - Navigator
[Route]
-> 스마트폰에 보여지는 하나의 페이지 또는 화면
[Navigator]
-> 네비게이터란 Route를 스택 자료구조로 관리한다.
-> 스택 자료구조에 대해서 push 와 pop 메소드를 제공한다.
-> Navigator에서 데이터를 쌓을 때에는 push method 를 사용
-> 데이터를 없앨 때에는 pop method 사용
[push]
-> 페이지의 생성은 push method를 사용한다.
[Navigator의 요구 인자]
-> Navigator는 context 와 route를 인자로 요구한다.
-> context가 가지고 있는 위젯 트리의 위치 정보에 근거해서, 현재 화면 상에 보여주는 페이지가 어떤 페이지인지 확인하고 이 페이지 위에 푸쉬 함수가 이동하기 원하는 새로운 라우트를 쌓아 올려야 하기 때문이다.
-> FirstPage 위로 SecondPage를 쌓아 올리기 위해서는 FirstPage 의 위치를 정확히 알아야 하기 때문에 FirstPage 의 context가 필요하다.
-> route 부분에는 바로 SecondPage가 오는게 아니라 MaterialPageRoute( builder: builder) 가 들어간다.
-> builder는 어떤 위젯이 MaterialPageRoute의 도움을 받아 생성 될 지 정의하는 속성
-> 바로 이동할 위젯을 넣는게 아니라 굳이 MaterialPageRoute와 builder를 거쳐서 가는 이유는 라우트 호출 간에 생길 수 있는 에러를 builder를 사용하여 미연에 방지하도록 안전 장치를 거는 것이다.
[pop]
-> pop 은 이전보다 더 간단하다.
-> first page 위에 second page가 올라와 쌓여있는 스택 구조이기 때문에 기존 second page를 걷어내면 first page가 나오게 된다.
-> 이 뒤로가기 버튼은 Scaffold를 사용해서 앱바를 생성하면 자동으로 플러터가 페이지 이동시 뒤로가기 버튼을 만들어준다.
-> 그래서 굳이 pop method를 구현하지 않아도 된다.
-> 앱바를 생성하지 않을 때 뒤로가기 기능을 구현하기 위해서는 pop이 필요하다.
[최종 코드]
import 'package:flutter/material.dart';
void main(List<String> args) {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return MaterialApp(
debugShowCheckedModeBanner: false,
title: 'Navigator',
theme: ThemeData(primarySwatch: Colors.blue),
home: FirstPage(),
);
}
}
class FirstPage extends StatelessWidget {
const FirstPage({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text('First Page'),
//centerTitle: true,
),
body: Center(
child: ElevatedButton(
child: Text('Go to the Second Page'),
onPressed: (){
Navigator.push(context, MaterialPageRoute(
builder: (_) => SecondPage()));
},
),
),
);
}
}
class SecondPage extends StatelessWidget {
const SecondPage({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text('Second Page'),
//centerTitle: true,
),
body: Center(
child: ElevatedButton(
child: Text('Go to the First Page'),
onPressed: (){
Navigator.pop(context);
// 기존 First page 위에 쌓여있던 Second Page가 없어지는 것
},
),
),
);
}
}