이번포스팅에서는 이미지 불러오기를 해보겠습니다.
이미지를 불러오는 방법은 두가지가 있습니다.
1. 네트워크를 통해서 즉 인터넷에서 받아오는방법
2. 지금 만들고있는 앱에 내장된 이미지를 불러오는방법
두가지 모두 장단점이 있습니다.
1. 네트워크 즉 서버에 저장된 이미지. 쉽게말해서 인터넷에서 다운을받아 보여줄경우,
인터넷 속도에 영향을 받을수가 있습니다. 1~2초뒤에 이미지가 나올수있다는거죠, 용량이큰 이미지면 5초넘게 걸릴수도 있겟죠,
또한 가져오는 이미지가 삭제되면 오류가 날수도 있습니다.
그러나 최소한 이미지 때문에 앱자체의 용량이 커지는건 막을수 있습니다..
2 앱에 내장된 이미지를 불러온다고 했을때,
요즘 이미지 용량이 엄청 큰것도 많은데, 아무리 용량이 작더라도 이미지가 엄청많으면 앱자체의 용량이 커져서
앱스토어에서 다운받으려면 40, 50 메가 넘을수도 있게 되겠죠.
그래서 너무 많은 이미지를 넣으면 앱 용량이 커집니다.
그래서 이 두가지 방법을 적절하게 사용해야합니다.
먼저 1번 인터넷에서 이미지 가져오는 방법을 먼저 해보겠습니다.
1. 인터넷에 있는 이미지 불러오기
첫번째 페이지있던 내용들을 지우고 다음과 같이 네모박스한개를 만들어줍니다.
가로 200 세로 200 정사각형 박스를 만들었습니다.
컨테이너에 테두리를 주기위해서는
decoration 옵션을 사용하면됩니다. decoration 옵션은 BoxDecoration 이라는 위젯을 받습니다.
그다음 child 에 Image.network() 라는 위젯을 줍니다.
아래처럼 작성해주세요.
Image.network('이미지Url') 괄호안에는 이미지의 url주소를 넣으면됩니다.
https:// 로 시작하는 이미지 주소를 넣어주세요.
이렇게 하면 이미지가 불어와 졌습니다.
주소가 너무길어서 관리하기가 힘드네요.
변수에 담아서 사용하겠습니다.
박스를 200, 200 줬는데 빈공간이 남네요.
이미지가 작아서 그런걸까요?
2. BoxFit 옵션
결론부터 말씀드리자면 이미지가 작아서 그런것은 아닙니다.
기본적으로 contain 이라는 옵션을 가지고 있기 때문입니다.
다음과 같이 fit:BoxFit.fill 로 바꿔볼게요.
이렇게 하니 원본과 다르게 비율이 달라지긴했지만 어쨋든 꽉채우네요.
cover 로 바꿔봤습니다.
그러니 이미지의 원본비율은 유지(이미지가 깨지지않음) 되었지만 이거같은경우 양옆에 잘려버렸네요.
이미지의 fit 옵션에서
가장많이 사용하는게
contain
cover
fill
입니다.
contain - 이미지 의 세로, 가로길이중 긴것을 부모사이즈에 맞추고 나머지는 빈공간으로 남긴다.
cover - 이미지 의 세로, 가로길이중 짧은것을 부모사이즈에 맞추가 긴부분이 영역을 벗어난것은 잘라버린다.
fill - contain 처름 긴것을 부모사이즈에 맞추고 나머지는 늘려서 부모사이즈에 맞춘다.
입니다. 상황에 맞춰서 사용하시면 됩니다.
어쨋든 이렇게 이미지를 불러왔습니다.
그런데 만약 불러오던 이미지의 주소가 바뀌거나 잘못했거나 무슨이유던지 오류가 발생하면 앱이 정상작동하지 않을수있습니다.
3. errorBuilder
그래서 에러일때 처리해주는게 필요한데
errorBuilder 라는 옵션입니다.
그런데 이것은 error 를 탐지한뒤, 상태를 바꿔주는 그런 로직이 되어있습니다.
"상태를 바꿔준다" 라는것은 상태를 바꾸는게 허락된 위젯에서 사용할수 있습니다.
그것이 StateFul 위젯이죠.
지금 우리가 하고있는 위젯은 stateless 위젯입니다.
애초에 우리가 만들때 StatelessWidget 으로 만들었었죠.
위젯에는 2가지가 있습니다.
상태가 변하지 않고 처음 상태를 유지하는 위젯 - statelesswidget
상태가 변할수 있는위젯 - statefulwidget
어쨋든 이거를 statefulwidget 으로 바꿔줄건데
처음부터 새로 작성할수는 없고, statelesswidget에 마우스를 가져다대고 Alt+enter 친뒤 statefulwidget으로 바꿔줍니다.
StatefulWidget 으로 바꾸고 난뒤
Image.network 위젯의 옵션적는쪽에
errorBuilder 를 추가해줍니다.
errorBuilder: (BuildContext context, Object exception, StackTrace stackTrace) {return Text('에러입니다 ㅠㅠ');},
이렇게 하면 주소가 틀리던지 무슨이유에서든 에러가 나면 우리가 지정한것을 나타내줍니다.
(일부로 주소에 아무글자나 넣어서 오류나도록 만들었습니다.)
그러면 아이디어가,
앱내부에 이미지에러일때 나타내줄 이미지를 저장하고 있다가,
네트워크 오류가 나면 errorBuilder를 통해 내부이미지를 보내주면 될거 같다는 생각이 듭니다.
그래서 다음은 앱내부이미지를 사용하는 방법을 알아보겠습니다.
4. 폴더 만들고 이미지넣기
왼쪽 폴더 트리에 제일 상단
저 같은경우는 helloman 이라는 폴더겠네요.
여기에 New - Directory를 선택해주세요.
폴더 만든다고 생각하시면 됩니다.
그리고 폴더명을 적어주세요.
보통 assets 이라고 많이 적지만 어떻게 짓든 자기마음입니다.
저는 myassets 라고 지을게요
그러면 이렇게 myassets 이라고 폴더가 하나 생기네요.
여기에다가 mytestimage 이라는 폴더를 하나 더 생성해보겠습니다.
이렇게 내부에 한개의 폴더가 또 생성됫네요.
그럼 계속해서 폴더구조를 만들어낼수있겠죠?
어쨋든 여기에 이미지파일을 하나 넣어보겠습니다.
들고계신 이미지 파일이 있다면 드레그앤 드롭으로 그냥 넣어주시면 됩니다.
이렇게 이미지를 넣어봤습니다.
5. pubspec.yaml 파일 건들기
pubspec.yaml 파일에 들어가주세요.
그러면 빨강 동그라미와 같이, assets : 이하 #으로 주석처리가 되어 있습니다.
# assets:
# - images/a_dot_burr.jpeg
# - images/a_dot_ham.jpeg
이부분을 주석처리를 풀어주세요. 방법은 앞에 #을 지우시면되는데
편하게 commend+/ 하시면됩니다.
그리고 라인을 잘 맞춰서 아래처럼 수정해주세요.
엄청 중요한 부분입니다.
이렇게 적으면 -myassets 폴더의 mytestimage 폴더 이하의 모든 파일을 사용하겠다고 하는것입니다.
' / ' 이거 잘 적어주세요. 마지막에 / 넣는거 까먹지 마시구요.
이렇게 한뒤 Pub get 을 눌러주세요.
6. 앱 내부 이미지 가져오기
네트웍 이미지를 불러왔던 그 페이지로 가주세요.
원래 Container 가 한개만 있었고 그안에 child로 이미지를 넣었었죠?
그걸 Column 으로 감싼뒤에 Container 를 2개로 만들어주세요.
그리고 아래 Container 의 child 부분에 Image.asset() 을 적어주세요.
() 여기에 우리가 불러올 이미지의 경로를 적어주시면 됩니다. fit옵션도 함께 적어볼게요.
이렇게 적을게요.
Image.asset('myassets/mytestimage/testcat.jpeg',fit: BoxFit.contain,)
이렇게 하니 이미지가 잘 불러와지네요.
그럼 이미지 한개더 받아볼게요.
인터넷에서 noimage 경고 이미지를 하나 다운받습니다.
진짜 아무거나 그냥 일단 다운받습니다.
그다음 처음에 우리가 네트워크 이미지 불러올때 오류일때 처리를 해줘야 한다고 했잖아요.
그거 처리를 해볼게요.
이부분이요.
지금은 오류일때 Text 로 에러입니다 ㅠㅠ. 라고 나오게 했잖아요?
여기에 return 을 다음과 같이 바꿔주세요.
이렇게 하면
오류가 날경우 우리가 다운받았던 오류 이미지가 나오게됩니다.
네트워크 이미지 경로에 마지막에 아무글자나 넣어서 경로를 틀리게 해보세요.
저는 경로 끝에 ㅇ 하나를 붙여줬어요.
그다음 초록색 run 버튼을 눌러서 재실행 해보세요.
그러니까 오류가 뜨면서 no image가 나오게됩니다.
이렇게 기본적으로 이미지 불러오기를 해봤습니다.
-----------------공지-------------------
23년 버전 앱강의를 오픈했습니다. 관심있으신분은 클릭 ㅋㅋ
2023.07.29 - [코딩생초보를 위한 플러터 빠르게 한바퀴] - 1. create project
개인과외 문의 saran.flutter@gmail.com