Don't think! Just do it!

종합 IT 기술 정체성 카오스 블로그! 이... 이곳은 어디지?

Flutter/Flutter Study

React Native에서 Flutter로 갈아타기 #6 - Props 전달

방피터 2022. 10. 6. 13:26

React Native에서는 하위 컴포넌트로 데이터를 전달할 때 props을 사용했지. 👇👇

import React, { useState,useEffect } from 'react';
import { Text, TouchableOpacity, View, Button } from 'react-native';

function App() {
  const [number, setNumber] = useState(0);

  const onIncrease = () => {
    setNumber(prev => prev + 1);
    console.log(number);
  }
  const onDecrease = () => {
    setNumber(prev => prev - 1);
    console.log(number);
  }
  return (
    <View style={{padding: 10}}>
      <Text>{number}</Text>
      <TextButton buttonText="ADD" onPressfn={onIncrease}/>
      <TextButton buttonText="SUB" onPressfn={onDecrease}/>
    </View>
  );
}
const TextButton = (props) => {
  const {buttonText, onPressfn} = props;
  return (
      <Button onPress={onPressfn} title={buttonText} />
    );
}
export default App;

TextButton이라는 자식 component를 만들고 props를 통해서 buttonText와 onPressfn 함수를 전달받도록 해놨어. 그리고 부모 컨테이너에서 TextButton을 호출하면서 props를 할당하여 사용하지.

React native props 전달

자 이제 저걸 똑같이 Flutter로 만들어 보자고. 우선 state를 가지고 있는 부모 위젯과 스테이트가 없는 자식 버튼 위젯을 만들면 되겠네?

먼저 Counter라는 StatefulWidget을 만들고 자식 버튼 위젯들을 호출했어.

class Counter extends StatefulWidget {
  const Counter({super.key});

  @override
  State<Counter> createState() => _CounterState();
}

class _CounterState extends State<Counter> {
  int counter = 0;		//counter

  @override
  Widget build(BuildContext context) {
    void increase() {
      setState(() {		//setState
        counter++;
      });
    }
    void decrease() {
      setState(() {		//setState
        counter--;
      });
    }
    return Column(
      children: [
        Text(counter.toString()),
        MyButton(buttonText: "ADD", buttonFn: increase),
        MyButton(buttonText: "SUB", buttonFn: decrease),
      ],
    );
  }
}

class MyButton extends StatelessWidget {
  const MyButton({super.key, required this.buttonText, required this.buttonFn});
  final String buttonText;
  final Function buttonFn;

  @override
  Widget build(BuildContext context) {
    return TextButton(onPressed: () => buttonFn(), child: Text(buttonText));
  }
}

React와 비교하자면 flutter가 조금 더 코드가 길다 그치? ㅋㅋㅋ 농담이고 React 에서는 컴포넌트에 data를 전달하려면 props 통해서 하고, Flutter는 딱히 props이라던가 하는게 없고 생성자(class하고 같은 이름의 함수)에 required로 선언하고 동일한 로컬 변수(final)를 선언해주면 돼. 한번 해보자구. 뭔가에 익숙해지려면 한 10번씩은 해봐야지 ㅋㅋ 코딩은 망치질이랑 비슷하다구!!

flutter - 자식에 data 전달 테스트

그런데 Statefulwidget에서는 약간 틀려. 위의 Mybutton  클래스를  StatefulWidget 으로 변경하고 버튼을 누를때마다 버튼 색을 변하게 하는 쓰잘데기 없는 state 하나를 넣어볼게. 👇👇 

class MyButton extends StatefulWidget {
  const MyButton({super.key, required this.buttonText, required this.buttonFn});
  final String buttonText;
  final Function buttonFn;
  @override
  State<MyButton> createState() => _MyButtonState();
}

class _MyButtonState extends State<MyButton> {
  bool checked = false;
  @override
  Widget build(BuildContext context) {
    return TextButton(
        style: TextButton.styleFrom(
            backgroundColor: checked ? Colors.amber : Colors.blueGrey),
        onPressed: () {
          setState(() {
            checked = !checked;
          });
          widget.buttonFn();			//이런식
        },
        child: Text(widget.buttonText));	//이런식
  }
}

이때는 StatefulWidget과 state과 나뉘어 있어서 StatelessWidget와는 다르게 곧바로 변수에 접근할 수 없고 widget.buttonText 이런 식으로 접근할 수 있어. 

flutter - 자식에 data 전달 테스트

 그런데 어떤 변수나 state를 여러 자식에서 사용해야 하거나 해야 할 경우에는 react에서도 큰 어려움이 있었지. 자식으로 계속 props를 전달할 수도 없는 노릇이고 ㅎㅎ 그래서 Hook을 사용한다던지, redux같은 state 관리 전용 툴들을 사용했었어.  나같은 경우는 recoil을 사용했었고.. flutter에도 redux나 recoil 패키지나 hook같은 것들도 있는 거 같아. 그런데 문서에서 flutter 초심자라면 provider라는 패키지를 사용할 것을 추천하고 있어.

state관리할 때는 provider를 쓰세요~

이건 조금 해야할 게 많으니까 다음에 하자고! 안녕!

반응형