2013
임베디드월드

글: 제갈호준 / 2013-11-05





지금까지 타이젠 플랫폼을 이해하기 위한 기초 지식을 알아봤다. 이번 호부터는 직접 타이젠 애플리케이션을 개발해보도록 한다. 처음 타이젠을 접하는 분들을 위해 가급적이면 따라 하기 방식으로 차근차근 진행할 예정이다.


[연재 차례]

1. 타이젠, 리눅스 기반 오픈소스 플랫폼
2. 타이젠 SDK(1)
3. 타이젠 SDK(2)
4. 타이젠 플랫폼의 이해
5. 타이젠 웹 애플리케이션 개발(1)
6. 타이젠 웹 애플리케이션 개발(2)
7. 타이젠 네이티브 애플리케이션 개발(1)
8. 타이젠 네이티브 애플리케이션 개발(2)
9. 타이젠 개발자 서밋 코리아 2013
10. 타이젠 플랫폼 개발



타이젠 시리즈 (7)

타이젠 네이티브 애플리케이션 개발 ①


네이티브 UI 애플리케이션


네이티브 UI 애플리케이션은 네이티브 애플리케이션 프레임워크와 네이티브 UI 프레임워크 기반으로C++ 언어를 사용하여 개발할 수 있다[1]. 네이티브 애플리케이션 프레임워크는 Tizen::App 네임스페이스로 구현되어 있는데, 이 안의 Tizen::App:App클래스가 네이티브 UI 애플리케이션의 실행과 라이프 사이클을 관리한다.



[그림 1] 네이티브 UI, 그래픽 아키텍처 (출처 : 자체 제작)



[표 1] Tizen::Ui 네임스페이스


그림 1은 타이젠 네이티브 UI와 그래픽 프레임워크의 아키텍처를 보여준다.
타이젠은 EFL(Enlightenment Foundation Li braries)[2]을 코어 UI 프레임워크로 사용한다. EFL은 2D와 2.5D UI 렌더링을 지원하는 라이브러리로서, 일반적인 GUI 위젯 뿐만 아니라 입력 처리, 데이터 관리 및 이벤트 관리 기능 등을 제공한다.


네이티브 UI 프레임워크는 EFL 라이브러리 중 하나인 Evas를 캔버스 그래픽을 위해 사용하고, ECore를 메인 이벤트 루프(loop)로 사용한다. 그 외에 OpenGL 및 OpenGL-ES 2.0은 게임과 같은 Open GL 기반 네이티브 애플리케이션을 작성할 때 쓰인다.


그래픽을 처리하기 위해 Cairo를 벡터 그래픽 기반의 2D 그래픽 라이브러리로 사용한다. Cairo와 EFL은 옵션에 따라 내부적으로 EGL (OpenGL)과 OpenGl-ES를 사용하거나 소프트웨어 렌더러를 사용한다. EGL은 OpenGL ES API와 2D, 3D 렌더링을 위한 그 기반에 깔려 있는 윈도우 시스템간의 인터페이스이며, OpenGL-ES는 OpenGL 3D 그래픽 API 중 임베디드 용으로 일부분을 뽑아놓은 API이다.
타이젠 네이티브 UI 프레임워크는 이러한 코어 UI 프레임워크에 기반하여 표 1과 같은 Tizen::Ui::* 네임스페이스들을 제공한다.




[그림 2] 윈도우 구조 (출처: developer.tizen.org)


네이티브 UI 애플리케이션의 종류


타이젠 아키텍처를 개괄적으로 살펴보면 크게 네이티브 UI 애플리케이션의 종류는 폼 기반(form-based), 테마(theme), 입력기(IME), OpenGL 기반, 탭 기반이 있다.
그 중에서 폼 기반 애플리케이션이 가장 기본이 되는 UI 애플리케이션이며, 다른 애플리케이션 템플릿들은 폼 위에 추가적인 사항들을 더했다고 생각하면 되겠다.


그림 2는 폼 기반 애플리케이션의 구조를 보여준다. 폼 기반 애플리케이션은 프레임, 폼, 컨트롤로 구성되는데, 프레임은 자동으로 생성 되는 최상위 윈도우이며 자신이 가지고 있는 폼을 화면에 보여주는 역할을 한다.
또한 Frame은 Form을 포함한 모든 UI 컨트롤 클래스들의 최상위 클래스로서 애플리케이션이 초기화 될 때 반드시 생성되어야 한다.
폼은 화면 전체에 표시되는 컨트롤로서 인디케이션 바, 헤더, 푸터, 그리고 다른 UI 컨트롤들로 이루어져 있다. 헤더와 푸터는 화면의 상단과 하단에 각각 배치된다.


서비스 애플리케이션(Service Application)

타이젠 네이티브 애플리케이션 프레임워크는 UI 애플리케이션 외에 서비스 애플리케이션을 제공한다. 서비스 애플리케이션은 사용자 인터페이스 없이 백그라운드에서 실행되는 애플리케이션을 말한다. 이러한 프로그램은 센서 데이터를 얻어내는 것처럼 지속적으로 실행되어야 하는 프로그램을 개발하는데 적당하다. 서비스 애플리케이션은 네이티브 UI 애플리케이션이나 웹 애플리케이션과 함께 패키징이 가능하다.

표 2. 서비스 애플리케이션 개념


네이티브 UI 애플리케이션 라이프 사이클


네이티브 애플리케이션 프레임워크는 프로그램 실행이나 전화 걸기와 같은 내장된 시스템 서비스 애플리케이션에 관련된 사항을 관리한다. 또한 메모리 경고나 배터리 사용량, 화면 오리엔테이션 전환, 푸시 알림과 같은 일반적인 이벤트들을 알려준다.
이러한 사항들은 Tizen::App 네임스페이스가 구현하고 제공한다.



[그림 3] 네이티브 UI 애플리케이션 상태 전환 흐름도 (출처 : developer.tizen.org)


그림 3은 네이티브 UI 애플리케이션의 기본적인 라이프 사이클을 UiApp과 Frame 클래스에서 발생하는 콜백을 기반으로 보여준다.


초기 상태에서 애플리케이션 프레임워크는 말 그대로 애플리케이션을 초기화시킨다. 이 시점에 저장된 애플리케이션 데이터를 복구시킬 수 있고, 애플리케이션의 프레임이 생성되어야 한다. 실행 중에는 사용자가 UI와 상호작용 할 수 있으며, 네이티브 애플리케이션은 백그라운드(background)와 포어그라운드(foreground) 상태를 반복 이동한다.


애플리케이션은 종료 단계에서 리소스를 해제하고 저장해야 할 사항들을 저장한다. 종료가 완료된 후에는 애플리케이션 프레임워크가 애플리케이션을 메모리로부터 제거한다.



[그림 4] UiApp 상태 변화 (출처 : 자체 제작)


<애플리케이션의 실행, 종료>


사용자는 디바이스의 메인 메뉴나, 태스크 스위처(task switcher) 혹은 다른 애플리케이션을 통해 네이티브 UI 애플리케이션을 실행할 수 있다.
사용자가 현재 실행되지 않고 있는 애플리케이션을 메인 메뉴에서 선택할 때, 애플리케이션이 실행된다. 만약 이미 실행되고 있는 애플리케이션을 메인 메뉴나 태스크 스위처에서 실행하면, 백그라운드에 있던 애플리케이션은 포어그라운드로 상태로 전환된다.


애플리케이션의 진입점은 OspMain() 함수다. 애플리케이션 초기화 단계에서 Tizen::App::App의 OnAppInitializing() 이벤트 핸들러가 호출되며, 이곳에서 전에 저장했던 애플리케이션 데이터를 Tizen::App::AppRegistry 클래스를 통해 얻어낼 수 있다. 이 이벤트 핸들러가 호출된 이후에, 애플리케이션은 리소스를 할당하고 UI 컨트롤들을 생성하게 된다.
애플리케이션 초기화가 끝나면, App::On Ap pInitialized() 이벤트 핸들러가 호출되며, 이 함수가 끝나기 전까지 프레임이 생성되고, 추가되어 있어야 한다.


실행되고 있는 애플리케이션은 Tizen::App:: App의 Terminate() 함수를 호출하면 스스로를 종료시킬 수 있다.
또한, 가용 메모리가 매우 적거나, 배터리가 없을 때, 시스템은 애플리케이션을 강제 종료시킬 수도 있다. 애플리케이션 종료 시에는 App 클래스의 OnAppTerminating() 이벤트 핸들러가 호출된다. 이 함수가 호출될 때, 직접 생성한 리소스들을 해제해 주어야 한다. 폼을 비롯한 그 자식 UI 컨트롤들은 Tizen::Ui:: Controls::Frame 클래스의 OnTerminating() 이벤트 핸들러가 호출될 때 해제된다.


<포어그라운드, 백그라운드>
네이티브 UI 애플리케이션의 윈도우는 그림 4와 같은 상태를 갖는다. Tizen::App::UiApp 클래스의 GetAppUiStates() 함수는 현재 애플리케이션의 상태를 반환한다.
Tizen::App::UiApp 클래스의 OnBackground() 이벤트 핸들러는 홈 키가 눌렸거나, 다른 애플리케이션이 실행되었거나, 잠금 화면이 되어 현재 애플리케이션이 활성화되지 않을 때 호출 된다. 이 함수가 호출될 때는, 진행 중이던 그래픽 처리나 미디어 처리, 센서, 위치 업데이트 등을 중지시키고, 현재의 데이터를 저장하는 것이 좋다.


OnForeground() 이벤트 핸들러는 UI 애플리케이션이 포어그라운드로 변경되었을 때 호출되며, 이 때부터 사용자 상호작용이 허용되며, 그래픽 처리 혹은 진행중인 미디어 재생과 같은 동작을 이전에 백그라운드로 전환될 때 저장한 데이터에 기반하여 다시 진행시키면 된다.



[그림 5] 빈 애플리케이션 생성하기 (출처 : 자체 제작)



[그림 6] 폼 클래스의 생성 (출처 : 자체 제작)


폼 생성과 이벤트 핸들링 예제


타이젠 IDE에서 템플릿을 이용하여 폼 기반의 애플리케이션을 만들 수 있다.
이번 예제에서는 템플릿 대신에 Empty Application을 선택하여 사용해 보도록 하자. IDE의 메뉴에서, File ->New -> Tizen Native Project를 선택하자. 그 다음 나타난 New Tizen Native Project 창에서 Template 탭을 선택하고, Empty Application을 선택한다. 그림 5와 같이 프로젝트 이름으로 “FormAndEvent”이라 입력하고 Finish 버튼을 클릭하자.


앞서 언급했듯이 Tizen::Ui 네임스페이스는 그래픽 유저 인터페이스를 생성하기 위해 사용된다. 또한 UI 관련 이벤트를 처리하기 위한 클래스와 인터페이스도 포함하고 있다.
보통, 폼을 생성하기 위해 Form 클래스를 상속받아 클래스를 구현한 후 해당 클래스를 프레임에 추가한다.



[표 3] 프레임에 폼을 추가하는 예제



[표 4] OnInitializing 및 OnTerminating 구현



[표 5] Onlnitializing 및 OnTerminating 구현(2)


1. Project Explorer에서 FormAndEvent 프로젝트를 오른쪽 클릭하자.
2. 나타나는 팝업 메뉴에서 New -> Class를 선택하자.
3. 그림 6과 같이 클래스에 “MyForm”이라 입력하고, Form을 베이스 클래스로 선택하자.
4. 이제 Project Explorer에 새로 추가된 MyForm.cpp과 MyForm.h을 확인할 수 있을 것이다. 폼이 동작하기 위해 폼을 프레임에 추가한 후, 현재 사용 폼으로 설정해야 한다. FormAndEventFrame.cpp에 표 3의 빨간색으로 표시한 부분을 코드에 추가하도록 하자.
5. OnInitializing과 OnTerminating 이벤트를 처리하기 위해 Form::OnInitializing()과 Form::On Terminating()을 구현해야 한다. 표 4의 빨간색으로 표시된 코드를 MyForm.h에 추가하자.
6. 표 5의 내용을 참고하여 MyForm.cpp을 수정한다.
7. 프로젝트를 빌드하고 에뮬레이터나 디바이스에서 실행하면 그림 7과 같은 아무것도 없는 빈 폼을 화면에서 볼 수 있을 것이다(그림 7).
8. 현재는 애플리케이션의 종료에 대해서 처리하지 않았기 때문에 해당 앱을 쉽게 종료시킬 수가 없다. 대신에, 홈 버튼을 길게 누르면 나타나는 태스크 스위처에서 FormAndEvent 애플리케이션을 찾아 End 버튼을 눌러서 종료시키도록 하자(그림 8)


[그림 7] 비어 있는 폼(좌측), [그림 8] FormAndEvent 애플리케이션을 종료하기 위해 불러낸 태스크 스위처 (각 출처: 자체제작)


위에서 OnInitializing()과 OnTerminating()에 AppLog를 넣었기 때문에, 그림 9와 같이 Log 창에서 로그를 확인할 수 있다. Tag 명에 애플리케이션 이름을 입력하면 내 애플리케이션에서 출력한 메시지만 필터링해서 볼 수 있다.



[그림 9] Log 창에서 FormAndEvent 애플리케이션 로그만 필터링한 상태 (출처 : 자체 제작)



[표 6] 터치 이벤트 처리(MyForm.h)



[표 7] 터치 이벤트 처리 (MyForm.cpp)


UI 이벤트 처리


UI 이벤트를 처리할 수 있어야만 터치, 키 입력, 사용자 동작, 애니메이션, 윈도우 변화 등과 같은 이벤트를 받아 처리할 수 있고, 비로소 애플리케이션이 사용자와 상호작용 할 수 있게 된다.
UI이벤트를 처리하기 위해 타이젠에서는 리스너(listener) 인터페이스를 사용하고 있다. 터치 이벤트는 ITouchEventListener를 상속받아 구현해야 하고, 키 이벤트는IKeyEventListener를 사용한다.
ITouchEventListener 인터페이스를 사용하여 터치 이벤트를 받기 위해 MyForm.h 파일에 표 6의 빨간색으로 표시된 코드를 입력해보자.


터치 프레스와 터치 릴리스 이벤트를 처리하기 위해 OnTouchPressed()와 OnTouchReleased()를 구현해야 한다. MyForm.cpp 파일에 표 7의 빨간색으로 표시된 부분을 입력하자.


이제 애플리케이션을 빌드하고 실행시킨 후 그림 8과 같은 빈 폼 위를 터치해보자.
Log 창에 OnTouchPressed와OnTouchReleased 로그가 애플리케이션의 폼 영역을 터치할 때마다 나타날 것이다. 위의 코드에서는 화면의 좌측 상단을 터치하면 애플리케이션을 종료하게 했다. 표 8은 애플리케이션이 실행된 후부터 종료할 때까지의 로그를 보여준다.



[표 8] 애플리케이션 실행부터 종료 시점까지 로그


마치며

이번 호에서는 타이젠 웹 UI 프레임워크 및 디바이스 API를 살펴보고 이를 활용한 샘플 애플리케이션을 제작해봤다.
웹 애플리케이션은 타이젠의 초기 생태계를 구축하는데 큰 축이 될 것이기 때문에 타이젠은 웹 애플리케이션을 위해 다양한 지원을 하고 있다. 이번 기회를 통해 웹 애플리케이션 개발에 참여해보는 것도 좋은 경험이 될 것이다.


참고

[1] https://developer.tizen.org/documentation/dev-guide
[2] http://jquerymobile.com
[3] https://developer.tizen.org/help/topic/org.tizen.web.device.apireference/index.html
[4] https://developer.tizen.org/help/topic/org.tizen.web.apppro gramming/html/guide/app_guide/application_service.htm
[5] https://developer.tizen.org/downloads/sample-web-applications

/필/자/소/개/

필자

제갈호준

삼성전자에서 타이젠 네이티브 아키텍처와 테스트 프레임워크 업무를 하였고, 현재는 스마트폰 서비스 플랫폼 개발에 힘쓰고 있다. Software Architecture, Information Retr ieval, Data Mining, Software Engineering, Auto mated Testing 등에 관심을 가지고 있으며 아이오와 주립대에서 박사학위를 취득하였다.





※ 본 내용은 (주)테크월드(http://www.embeddedworld.co.kr)의 저작권 동의에 의해 공유되고 있습니다.
    Copyright ⓒ Techworld, Inc. 무단전재 및 재배포 금지
맨 위로
맨 위로