React Native Style, Component 적용하기(Button, Button Event, 버튼, 버튼 이벤트)
리액트 네이티브를 이용하여 스타일CSS 및 컴포넌트를 적용하는 방법에 대해 포스팅 해보겠습니다.
Style 적용
리액트 네이티브 에서 스타일을 적용할 때 여러가지 방법이 있는데,
그 중에 인라인 스타일 코드 형식과 StyleSheet.create() 함수 호출하는 방식이 있다.
인라인 스타일 코드란?
컴포넌트의 style에 직접 스타일 코드를 작성하는 것을 인라인 스타일이라고 한다.
<View style={styles.container}>
<StatusBar style="auto" />
<Text style={{
fontSize: 30,
fontWeight: '700',
color: 'green',
backgroundColor: 'yellow',
borderWidth: 1,
borderColor: 'blue',
paddingHorizontal: 20,
paddingVertical: 10,
}}>Calc App</Text>
</View>
※ style 코드를 확인 해 보면 Json방식인 것을 확인 할 수 있다.
속성의 경우 camel case로 작성 해야 하고, px, em 등 단위를 사용하지 않는다.
인라인 스타일 외 리액트 네이티브에서 제공하는 StyleSheet를 사용하여 적용하는 방법도 있다.
const styles = StyleSheet.create({
container: {
flex: 1,
backgroundColor: '#fff',
alignItems: 'center',
justifyContent: 'center',
},
});
이처럼 StyleSheet.create() 함수를 호출하고, 매개변수는 Json형식이다.
스타일 시트를 추가하여 확인 해 보면
const App = () => {
return (
<View style={styles.container}>
<StatusBar style="auto" />
<Text style={styles.text}>Calc App</Text>
<Text style={styles.text}>StyleSheet</Text>
</View>
);
};
const styles = StyleSheet.create({
container: {
flex: 1,
backgroundColor: '#fff',
alignItems: 'center',
justifyContent: 'center',
},
text:{
fontSize: 30,
fontWeight: '700',
color: 'green'
}
});
아래 와 같이 확인 할 수 있다.
배열(JsonArray)또 한 적용 가능하다.
특정 상황에 따라 다른 스타일을 적용 할 수 있다. (IF)
import { StatusBar } from 'expo-status-bar';
import { StyleSheet, Text, View } from 'react-native';
const App = () => {
const isError = true;
return (
<View style={styles.container}>
<StatusBar style="auto" />
<Text style={styles.text}>Calc App</Text>
<Text style={styles.text}>StyleSheet</Text>
<Text style={[styles.text, isError && styles.error]}>Error</Text>
</View>
);
};
const styles = StyleSheet.create({
container: {
flex: 1,
backgroundColor: '#fff',
alignItems: 'center',
justifyContent: 'center',
},
text:{
fontSize: 30,
fontWeight: '700',
color: 'green'
},
error: {
fontSize: 30,
fontWeight: '700',
color: 'red'
}
});
export default App;
Button Component 적용
props -> properties의 줄임말
말 그대로 컴포넌트에 "속성"을 전달한다.
Button 컴포넌트를 사용한다면 title props가 반드시 문자열로 이루어져야 한다.
title과 onPress가 필수이다.(공식 문서)
import { StyleSheet, Text, View, Button } from 'react-native';
<Button title="button" onPress={ () => console.log('click !')} />
위 처럼 버튼을 추가 해 확인하면
title 내용이 IOS에서는 그대로 나타나지만, 안드로이드의 경우 대문자로 표현된다.
또 한 플랫폼별로 다 다르게 표현된다.
그리고 휴대폰에서 버튼을 클릭 했을 때 위 사진 처럼 IDE Run-Log에서 console.log가 찍히는 걸 확인 할 수 있다.
(console.log 설정 방법은 https://devdalbi.tistory.com/18 참고)
플랫폼별 입력한 코드의 값이 다르면 리액트를 사용 할 이유가 없다.
그래서 Style을 추가하여 이러한 문제를 해결해야 한다.
style={{backgroundColor: 'blue', color: 'white'}}
이렇게 스타일을 추가 해 보았지만, 변화가 없습니다.
왜냐면 Button 컴포넌트는 Style을 props로 받지 않기 때문에 스타일을 적용할 수 없습니다.
<Button title="button" onPress={ () => console.log('click !')} color="blue"/>
style 대신 color를 직접 입력하면 적용되는 것을 확인할 수 있습니다.
그렇다면 원하는 컴포넌트를 입력하고 싶다면 어떻게 해야 할까요 ?
컴포넌트 관련 JS 파일을 만들어 처리 해 보았습니다. (src/components/Button.js) (JSX 반환 규칙 참고하여 작성)
import { Text } from 'react-native';
const Button = (props) => {
console.log(props);
return <Text>버튼</Text>;
};
// 객체 구조 분해 할당법
const Button = ({ title }) => {
console.log(title);
return <Text>{title}</Text>;
};
export default Button;
// App.js
import Button from './components/Button';
버튼 함수의 매개변수를 console.log로 확인 해 보면 {"color": "blue", "onPress": [Function onPress], "title": "button"} 값을 가지고 있는 것을 확인 할 수 있습니다. 즉 {props.title} 찍어보면 "button" 값이 들어있는 것을 확인할 수 있습니다.
또 한 객체 구조 분해 문법을 이용하여 원하는 데이터를 추출할 수 있습니다.
테스트 중, prop-types lib는 여러 가지의 타입 검사 기능을 제공합니다.
npm install prop-types
설치 후 코드를 수정한 다음에
import PropTypes from 'prop-types';
Button.propTypes = {
title: PropTypes.string,
};
App.js
<Button title={100} onPress={ () => console.log('click !')} color="blue"/>
버튼 호출 시 에러가 발생 합니다.(문자열이 아닌 숫자가 들어가 에러를 발생)
title: PropTypes.string 부분에서 경고 메시지가 나타나는 것을 알 수 있습니다.
컴포넌트에 기본 값을 제공하고 싶다면 아래 코드를 추가 해 주면 됩니다.
Button.defaultProps = {
title: 'button title',
};
버튼 터치 시 효과 주기
import { TouchableHighlight } from 'react-native';
<TouchableHighlight
style={{backgroundColor: 'red', padding: 20}}
underlayColor="blue"
onPress={() => {}}>
<Text style={{color: 'white'}}>{title}</Text>
</TouchableHighlight>
underlayColor 터치 색 표현
버튼에 true / false 조건 주기
import { Pressable, Text } from 'react-native';
import PropTypes from 'prop-types';
const Button = ({ title }) => {
return (
<Pressable
style={(params) => {
console.log(params);
return {backgroundColor: 'red', padding: 20};
}}>
<Text style={{color: 'white'}}>{title}</Text>
</Pressable>
);
};
버튼을 누르고 있을 때 true, 누르고 있지 않을 때 false
참 거짓에 따라, 버튼 색 변경하기
const Button = ({ title }) => {
return (
<Pressable
style={({pressed}) => [
{backgroundColor: 'red', padding: 20},
pressed && { backgroundColor: 'black'}
]}>
<Text style={{color: 'white'}}>{title}</Text>
</Pressable>
);
};
※ 중괄호 생략가능
button 컴포넌트에서 press 이벤트 중 props가 호출되는 시점
onPressIn 터치 되었을 때
onPressOut 터치가 해제 되었을 때
onPress 터치가 해제 된 후 호출
onLongPress 일정 시간 동안 터치가 지속되었을 때