UI를 구성하는 모든 단위로 클래스의 인스턴스다. 그래픽이나 데이터를 처리하는 함수를 가진다. 각 위젯에는 named args를 넣어주게 된다.
상태가 없는 정적인 위젯이다. 스크린에 존재하면서 데이터를 저장하지 않고 아무 변화도 없다. 한 번 렌더링되면, 그 상태가 변하지 않는다. 데이터가 변하지 않거나 위젯이 다시 렌더링될 필요가 없는 경우에 사용한다. (로고, 아이콘 등)
class MyStatelessWidget extends StatelessWidget {
Widget build(BuildContext context) {
return Container(
child: Text('Hello, I am a stateless widget'),
);
}
}
계속해서 변화가 있는 위젯이다. 사용자의 인터렉션에 따라 변한다. 사용자 입력이나 API 응답과 같이 동적인 데이터를 처리하거나, 사용자와의 상호작용을 통해 상태가 변화하는 경우 사용한다.
플러터 프레임워크는 createState()를 통해 값이 동적으로 변하는 페이지를 렌더링한다.
class MyStatefulWidget extends StatefulWidget {
_MyStatefulWidgetState createState() => _MyStatefulWidgetState();
}
class _MyStatefulWidgetState extends State<MyStatefulWidget> {
int counter = 0;
void incrementCounter() {
setState(() {
counter++;
});
}
Widget build(BuildContext context) {
return Scaffold(
body: Center(
child: Text('Counter Value: $counter'),
),
floatingActionButton: FloatingActionButton(
onPressed: incrementCounter,
tooltip: 'Increment',
child: Icon(Icons.add),
),
);
}
}
class MyStatefulWidget extends StatefulWidget {
final Color color;
MyStatefulWidget({this.color});
_MyStatefulWidgetState createState() => _MyStatefulWidgetState();
}
class _MyStatefulWidgetState extends State<MyStatefulWidget> {
Widget build(BuildContext context) {
return Container(
color: widget.color,
);
}
}
상태(state)란 애플리케이션에서 시간이 지남에 따라 변경될 수 있는 데이터를 의미한다. StatefulWidget은 createState() 메소드를 통해 상태를 생성하고 관리한다.
플러터 프레임워크는 State와 같이 제너릭을 통해 반환된 State 인스턴스를 StatefulWidget과 연결한다. 이는 State 객체가 자신을 소유한 StatefulWidget에 대한 정보를 갖고 있어야 하기 때문이다. State는 StatefulWidget의 데이터를 읽고, 변경 사항이 있을 경우 setState()를 호출하여 화면을 다시 빌드한다.
setState() 메서드를 사용하면 변한 상태 값에 대해 리렌더링 해준다.
createState() 함수는 StatefulWidget의 인스턴스를 만들 때 호출되는 함수로, State 클래스의 인스턴스를 반환한다. State 인스턴스는 StatefulWidget의 생명주기 동안 지속되는 상태를 갖고 있다.
StatelessWidget은 상태를 유지하지 않기 때문에 createState와 같은 상태 관리 메서드가 필요하지 않다.
State 객체가 생성될 때는 widget 객체를 자동으로 생성한다. widget은 State 객체 내에서 사용할 수 있고, 현재 State 객체와 연결된 StatefulWidget 인스턴스를 참조한다. 즉, State 객체가 자신의 부모 StatefulWidget의 속성에 접근할 수 있도록 한다.
initState() 메서드는 State 객체가 생성될 때 한 번만 호출되며, 위젯이 초기화되는 로직을 넣는 곳이다.
데이터를 불러오거나, 스트림을 설정하거나, 애니메이션을 초기화하는 등의 작업을 수행할 수 있다. 위젯이 트리에 삽입되기 전에 호출되므로 화면이 그려지기 전에 준비해야 하는 모든 것을 설정하는 데 사용된다.
void initState() {
super.initState();
// initialize data, start animations, etc.
}
dispose() 메서드는 StatefulWidget이 위젯 트리에서 제거되기 전에 호출된다. 위젯이 더 이상 필요하지 않을 때 그 위젯과 관련된 모든 리소스를 정리하는 데 사용된다.
컨트롤러를 dispose하거나, 스트림을 닫거나, 메모리에 남아있는 객체를 삭제하는 등의 작업을 수행할 수 있다.
void dispose() {
// dispose resources like controllers, streams, etc.
super.dispose();
}