모바일 앱 개발 (플러터) #5

손현수·2023년 10월 11일
0

체크박스 만들기

체크박스를 만들 때 필요한 속성

  • bool 타입의 변수를 선언하여 Checkbox의 value가 참조할 수 있도록 해야 한다.
  • Checkbox의 onChanged 함수의 parameter로 value를 넣어줘야 한다. -> onChanged 함수가 하는 역할은 Checkbox가 클릭되었을 때 parameter로 받은 value가 참조하는 값을 부정하여 재할당하고 함수의 body의 코드를 실행함. 따라서 Checkbox가 클릭되었을 때 어떤 작업을 할지 onChanged 함수의 body에 구현하면 된다.
class _MyHomePageState extends State<MyHomePage> {
  bool _isChecked = false;

  
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Receive User Information'),
      ),
      body: Checkbox(
        value: _isChecked,
        onChanged: (value) {
          setState(() {
              _isChecked = value!;
          });
        },
      )
    );
  }
}

setState() 함수

  • setState() 함수는 우리가 앱에서 무언가 동작을 했을 때 ui가 업데이트되어야 하는 상황에서 사용하는 함수이다. 지금의 경우 Checkbox를 클릭했을 때 Checkbox의 ui가 업데이트가 되어야 하므로 Checkbox의 value로 활용되는 _isChecked 변수의 값을 onChanged 함수에 의해 클릭될 때마다 자동으로 변경되는 value의 값으로 업데이트하고 해당 업데이트를 ui에 반영하는 일을 한다.

value에 !가 있는 이유

  • onChanged 함수가 받는 value의 경우 타입이 bool? 이므로 null이 가능한 상황이다. 그런데 value의 값을 할당하는 _isChecked의 경우 null이 불가능하므로 value의 값이 null이 아님을 명시하기 위해 붙인 것이다.

CheckboxListTile 구현하기

  • 일반적으로 앱에서는 Checkbox를 단독으로 사용하는 경우는 없다. 텍스트와 같은 어떤 간단한 데이터 옆에 Checkbox를 두고 싶다면 CheckboxListTile을 사용하자
  • 추가적인 커스터마이징이 필요하다면 ListView와 곁들여서 Checkbox를 단독으로 사용하자
class _MyHomePageState extends State<MyHomePage> {
  bool _isChecked = false;
  bool _isChecked2 = false;
  bool _isChecked3 = false;

  
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Receive User Information'),
      ),
      body: ListView(
        children: [
          CheckboxListTile(
            title: Text('Test'),
            value: _isChecked,
            onChanged: (value) {
              setState(() {
                  _isChecked = value!;
              });
            },
          ),
          CheckboxListTile(
            title: Text('Test2'),
            value: _isChecked2,
            onChanged: (value) {
              setState(() {
                _isChecked2 = value!;
              });
            },
          ),
          CheckboxListTile(
            title: Text('Test3'),
            value: _isChecked3,
            onChanged: (value) {
              setState(() {
                _isChecked3 = value!;
              });
            },
          ),
        ],
      )
    );
  }
}

  • 위의 CheckboxListTile을 SwitchListTile로 변경하는 것이 가능하다.

RadioListTile 구현하기

RadioListTile의 여러 속성값 알아보기

  • groupValue: 현재 그룹에서 어떤 값이 선택되어 있는지를 나타내는 것. 따라서 이 값들은 서로 공유가 되어있어야 함. 현재는 enum의 형태로 공유
  • value: 지금 이 RadioListTile이 클릭되면 groupValue 속성에 할당된 변수에 어떤 값을 넣을지 나타내는 속성
  • onChanged(value): 클릭되었을 때 value에 할당된 값을 groupValue에 할당된 변수의 값에 할당하고 함수의 body에 있는 코드를 실행
enum Language {cpp, python, dart}

class _MyHomePageState extends State<MyHomePage> {
  Language _language = Language.cpp;

  
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Receive User Information'),
      ),
      body: ListView(
        children: [
          RadioListTile(
              title: Text('C++'),
              value: Language.cpp,
              groupValue: _language,
              onChanged: (value) {
                setState(() {
                  _language = value!;
                });
              }
          ),
          RadioListTile(
              title: Text('Python'),
              value: Language.python,
              groupValue: _language,
              onChanged: (value) {
                setState(() {
                  _language = value!;
                });
              }
          ),
          RadioListTile(
              title: Text('Dart'),
              value: Language.dart,
              groupValue: _language,
              onChanged: (value) {
                setState(() {
                  _language = value!;
                });
              }
          )
        ],
      ),
    );
  }
}

DropDownButton 구현하기

  • value에는 선택된 값을 저장할 변수를 할당한다.
  • items에는 DropDownButton의 메뉴에 어떤 것들을 넣을지 설정
  • onChanged(value)는 클릭되었을 때 어떤 작업을 실행할지 결정. DropDownButton의 아이템을 클릭한 순간 내가 클릭한 값이 onChanged(value)의 value에 저장이 되고 이 값으로 setState()의 body에서 DropDownButton의 value 속성에 할당된 변수의 값을 업데이트하면 선택된 값으로 ui가 업데이트된다.
class _MyHomePageState extends State<MyHomePage> {
  final _valueList = List.generate(10, (i) => 'Student $i');
  var _selectedValue = 'Student 0';

  
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Receive User Information'),
      ),
      body: Center(
        child: DropdownButton(
          value: _selectedValue,
          items: _valueList.map( (student) => DropdownMenuItem(
              value: student,
              child: Text(student)
            )
          ).toList(),
          onChanged: (value) {
            setState(() {
              _selectedValue = value!;
            });
          },
        ),
      ),
    );
  }
}

TextField 구현해보기

TextField의 속성 알아보기

  • decoration: InputDecoration의 labelText를 통해 입력하기 전 hint 텍스트 제공
  • controller: 입력이 완료되었을 때 실행될 함수
  • keyboardType: 클릭했을 때 실행되는 키보드를 설정
class _MyHomePageState extends State<MyHomePage> {
  final _heightController = TextEditingController();
  final _weightController = TextEditingController();
  String _obesity = 'Normal';

  void dispose() { // Widget이 사라졌을 때 실행하는 함수
    _heightController.dispose();
    _weightController.dispose();
    super.dispose();
  }

  
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Receive User Information'),
      ),
      body: Padding(
        padding: const EdgeInsets.all(16.0),
        child: Center(
            child: Column(
              mainAxisAlignment: MainAxisAlignment.center,
              children: [
                TextField(
                  decoration: InputDecoration(
                      border: OutlineInputBorder(),
                      labelText: 'Height'
                  ),
                  controller: _heightController,
                  keyboardType: TextInputType.number,
                ),
                Container(
                  height: 20,
                ),
                TextField(
                  decoration: InputDecoration(
                    border: OutlineInputBorder(),
                    labelText: 'Weight'
                  ),
                  controller: _weightController,
                  keyboardType: TextInputType.number,
                ),
                Container(height: 20,),
                Text(_obesity, style: TextStyle(fontSize: 20),),
                Container(height: 20,),
                ElevatedButton(onPressed: () {
                  setState(() {
                    var heightValue = double.parse(_heightController.text.trim());
                    var weightValue = double.parse(_weightController.text.trim());
                    if (weightValue / heightValue * heightValue > 25) {
                      _obesity = 'Obesity';
                    } else {
                      _obesity = 'Normal';
                    }
                  });
                }, child: Text('Enter'))
              ],
            )
        ),
      ),
    );
  }
}

profile
안녕하세요.

0개의 댓글